diff -Nru opencryptoki-3.18.0+dfsg/ChangeLog opencryptoki-3.20.0+dfsg/ChangeLog --- opencryptoki-3.18.0+dfsg/ChangeLog 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/ChangeLog 2023-02-13 09:22:42.000000000 +0100 @@ -1,3 +1,29 @@ ++ openCryptoki 3.20 +- Soft/ICA: add support for the AES-XTS key type (PKCS#11 v3.0) +- ICSF: add support for ECDH and additional SHA variants +- ICSF: add support for CKM_TLS_PRE_MASTER_KEY_GEN and CKM_TLS_KEY_AND_MAC_DERIVE +- EP11: add support for the EP11 host library version 4 +- EP11: add support for additional IBM specific Dilithium round 2 and 3 variants +- EP11: add support for the IBM specific Kyber key type and mechanism +- EP11: add support for the AES-XTS key type using CPACF protected keys +- p11sak: add support for the AES-XTS key type +- p11sak: add support for additional Dilithium variants and the Kyber key type +- Bug fixes + ++ openCryptoki 3.19 +- CCA: check for expected master key verification patterns at token init +- CCA: check master key verification pattern of created keys to be as expected +- EP11: check for expected wrapping key verification pattern at token init +- EP11: check wrapping key verification pattern of created keys to be as expected +- p11sak/pkcsconf: display PKCS#11 URIs +- p11sak: add support for IBM specific Dilithium keys +- p11sak: allow to list keys filtered by label +- common: add support for dual-function cryptographic functions +- Add support for C_SessionCancel function (PKCS#11 v3.0) +- EP11: add support for schnorr signatures (mechanism CKM_IBM_ECDSA_OTHER) +- EP11: add support for Bitcoin key derivation (mechanism CKM_IBM_BTC_DERIVE) +- Bug fixes + + openCryptoki 3.18 - Default to FIPS compliant token data format (tokversion = 3.12) - Add support for restricting usage of mechanisms and keys via a global policy diff -Nru opencryptoki-3.18.0+dfsg/cleanup.sh opencryptoki-3.20.0+dfsg/cleanup.sh --- opencryptoki-3.18.0+dfsg/cleanup.sh 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/cleanup.sh 2023-02-13 09:22:42.000000000 +0100 @@ -1,3 +1,11 @@ #!/bin/sh +# +# COPYRIGHT (c) International Business Machines Corp. 2001-2022 +# +# This program is provided under the terms of the Common Public License, +# version 1.0 (CPL-1.0). Any use, reproduction or distribution for this software +# constitutes recipient's acceptance of CPL-1.0 terms which can be found +# in the file LICENSE file or at https://opensource.org/licenses/cpl1.0.php +# -rm -rf `cat .gitignore`; +test -f Makefile && make maintainer-clean diff -Nru opencryptoki-3.18.0+dfsg/configure.ac opencryptoki-3.20.0+dfsg/configure.ac --- opencryptoki-3.18.0+dfsg/configure.ac 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/configure.ac 2023-02-13 09:22:42.000000000 +0100 @@ -1,6 +1,6 @@ dnl Process this file with autoconf to produce a configure script. AC_PREREQ([2.69]) -AC_INIT([openCryptoki],[3.18.0],[https://github.com/opencryptoki/opencryptoki/issues],[],[https://github.com/opencryptoki/opencryptoki]) +AC_INIT([openCryptoki],[3.20.0],[https://github.com/opencryptoki/opencryptoki/issues],[],[https://github.com/opencryptoki/opencryptoki]) AC_CONFIG_SRCDIR([testcases/common/common.c]) dnl Needed for $target! @@ -75,7 +75,6 @@ [OPENLDAP_LIBS="-llber -lldap"], [AC_MSG_ERROR([lber.h and ldap.h are missing. Please install 'openldap-devel'.])]) -LIBS="$LIBS $OPENLDAP_LIBS" AC_SUBST([OPENLDAP_LIBS]) dnl Define custom variables @@ -86,6 +85,8 @@ logdir=$localstatedir/log/opencryptoki AC_SUBST(logdir) +AM_CONDITIONAL([CROSS], [test "x$cross_compiling" = xyes]) + dnl --- dnl --- Check all --enable/--disable-features dnl --- @@ -141,7 +142,7 @@ dnl --- EP11 token AC_ARG_ENABLE([ep11tok], AS_HELP_STRING([--enable-ep11tok],[build ep11 token @<:@default=enabled - if zcrypt is present@:>@]), + if libica development files are present@:>@]), [], [enable_ep11tok=check]) @@ -163,13 +164,13 @@ dnl --- token-specific stuff dnl --- pkcsep11_migrate AC_ARG_ENABLE([pkcsep11_migrate], - AS_HELP_STRING([--enable-pkcsep11_migrate],[build pkcsep11_migrate (EP11 token key migration tool) @<:@default=enabled if EP11 library is present@:>@]), + AS_HELP_STRING([--enable-pkcsep11_migrate],[build pkcsep11_migrate (EP11 token key migration tool) @<:@default=enabled if EP11 token is enabled@:>@]), [], [enable_pkcsep11_migrate=check]) dnl --- pkcsep11_session AC_ARG_ENABLE([pkcsep11_session], - AS_HELP_STRING([--enable-pkcsep11_session],[build pkcsep11_session (EP11 token session logout tool) @<:@default=enabled if EP11 library is present@:>@]), + AS_HELP_STRING([--enable-pkcsep11_session],[build pkcsep11_session (EP11 token session logout tool) @<:@default=enabled if EP11 token is enabled@:>@]), [], [enable_pkcsep11_session=check]) @@ -194,6 +195,10 @@ AS_HELP_STRING([--enable-pkcsstats],[build pkcsstats tool @<:@default=enabled@:>@]), [], [enable_pkcsstats=yes]) + +dnl --- support for MD2 +AC_ARG_ENABLE([md2], + AS_HELP_STRING([--enable-md2],[build opencryptoki with support for MD2])) dnl --- dnl --- Check for external software @@ -211,24 +216,12 @@ [], [with_libica=check]) -dnl --- zcrypt development files -AC_ARG_WITH([zcrypt], - AS_HELP_STRING([--with-zcrypt@<:@=DIR@:>@],[zcrypt development files location]), - [], - [with_zcrypt=check]) - dnl --- TSS (TrouSerS) development files AC_ARG_WITH([tss], AS_HELP_STRING([--with-tss@<:@=DIR@:>@],[TrouSerS development files location]), [], [with_tss=check]) -dnl --- xcryptolinz development files (IBM CCA development files) -AC_ARG_WITH([xcryptolinz], - AS_HELP_STRING([--with-xcryptolinz@<:@=DIR@:>@],[CCA library (xcryptolinz) location]), - [], - [with_xcryptolinz=check]) - dnl --- systemd system unit files location AC_ARG_WITH([systemd], AS_HELP_STRING([--with-systemd@<:@=DIR@:>@],[systemd system unit files location]), @@ -335,40 +328,6 @@ AC_SUBST([LIBICA_CFLAGS]) AC_SUBST([LIBICA_LIBS]) - -dnl --- with_zcrypt -ZCRYPT_CFLAGS= -ZCRYPT_LIBS= -if test "x$with_zcrypt" != "xno"; then - if test "x$with_zcrypt" != "xyes" -a "x$with_zcrypt" != "xcheck"; then - ZCRYPT_CFLAGS="-I$with_zcrypt" - ZCRYPT_LIBS="-L$with_zcrypt" - fi - old_cflags="$CFLAGS" - old_libs="$LIBS" - CFLAGS="$CFLAGS $ZCRYPT_CFLAGS" - LIBS="$LIBS $ZCRYPT_LIBS" - AC_CHECK_HEADER([asm/zcrypt.h], [], [ - if test "x$with_zcrypt" != "xcheck"; then - AC_MSG_ERROR([Build with zcrypt requested but zcrypt headers couldn't be found]) - fi - with_zcrypt=no - ]) - - if test "x$with_zcrypt" != "xno"; then - with_zcrypt=yes - fi - - if test "x$with_zcrypt" = "xno"; then - CFLAGS="$old_cflags" - LIBS="$old_libs" - fi - -fi -AC_SUBST([ZCRYPT_CFLAGS]) -AC_SUBST([ZCRYPT_LIBS]) - - dnl --- with_tss TSS_CFLAGS= TSS_LIBS= @@ -404,42 +363,6 @@ AC_SUBST([TSS_CFLAGS]) AC_SUBST([TSS_LIBS]) -dnl --- with_xcryptolinz -XCRYPTOLINZ_CFLAGS= -XCRYPTOLINZ_LIBS= -if test "x$with_xcryptolinz" != "xno"; then - if test "x$with_xcryptolinz" != "xyes" -a "x$with_xcryptolinz" != "xcheck"; then - XCRYPTOLINZ_CFLAGS="-I$with_xcryptolinz" - XCRYPTOLINZ_LIBS="-L$with_xcryptolinz" - fi - old_cflags="$CFLAGS" - old_libs="$LIBS" - CFLAGS="$CFLAGS $XCRYPTOLINZ_CFLAGS" - LIBS="$LIBS $XCRYPTOLINZ_LIBS" -dnl - The above may not be necessary since opencryptoki brings this header file anyway. - AC_CHECK_HEADER([csulincl.h], [], [ - if test "x$with_xcryptolinz" != "xcheck"; then - AC_MSG_ERROR([Build with xcryptolinz requested but xcryptolinz headers couldn't be found]) - fi - with_xcryptolinz=no - ]) - if test "x$with_xcryptolinz" != "xno"; then - AC_CHECK_LIB([csulcca], [CSNBKTC], - [with_xcryptolinz=yes], [ - if test "x$with_xcryptolinz" != "xcheck"; then - AC_MSG_ERROR([Build with xcryptolinz requested but xcryptolinz libraries couldn't be found]) - fi - with_xcryptolinz=no - ]) - fi - if test "x$with_xcryptolinz" = "xno"; then - CFLAGS="$old_cflags" - LIBS="$old_libs" - fi -fi -AC_SUBST([XCRYPTOLINZ_CFLAGS]) -AC_SUBST([XCRYPTOLINZ_LIBS]) - dnl --- with_libudev LIBUDEV_CFLAGS= LIBUDEV_LIBS= @@ -560,19 +483,21 @@ dnl --- enable_ep11tok if test "x$enable_ep11tok" = "xyes"; then - if test "x$with_zcrypt" != "xyes"; then - AC_MSG_ERROR([ep11 token build requested but ep11 development files not found]) - enable_ep11=no - fi AC_CHECK_HEADER([ica_api.h], [], [ AC_MSG_ERROR([ep11 token build requested but Libica headers couldn't be found]) ]) + AC_CHECK_HEADER([asm/pkey.h], [], [ + AC_MSG_ERROR([ep11 token build requested but Kernel's pkey header couldn't be found]) + ]) fi -if test "x$enable_ep11tok" != "xno" -a "x$with_zcrypt" != "xno"; then +if test "x$enable_ep11tok" != "xno"; then enable_ep11tok=yes AC_CHECK_HEADER([ica_api.h], [], [ enable_ep11tok=no ]) + AC_CHECK_HEADER([asm/pkey.h], [], [ + enable_ep11tok=no + ]) else enable_ep11tok=no fi @@ -609,12 +534,12 @@ dnl --- enable_pkcsep11_migrate if test "x$enable_pkcsep11_migrate" = "xyes"; then - if test "x$with_zcrypt" != "xyes"; then - AC_MSG_ERROR([pkcsep11_migrate build requested but no ep11 libraries found]) + if test "x$enable_ep11tok" != "xyes"; then + AC_MSG_ERROR([pkcsep11_migrate build requested but the ep11 token is not enabled]) enable_pkcsep11_migrate=no fi fi -if test "x$enable_pkcsep11_migrate" != "xno" -a "x$with_zcrypt" != "xno"; then +if test "x$enable_pkcsep11_migrate" != "xno" -a "x$enable_ep11tok" = "xyes"; then enable_pkcsep11_migrate=yes else enable_pkcsep11_migrate=no @@ -623,13 +548,13 @@ dnl --- enable_pkcsep11_session if test "x$enable_pkcsep11_session" = "xyes"; then - if test "x$with_zcrypt" != "xyes"; then - AC_MSG_ERROR([pkcsep11_session build requested but no ep11 libraries found]) + if test "x$enable_ep11tok" != "xyes"; then + AC_MSG_ERROR([pkcsep11_session build requested but the ep11 token is not enabled]) enable_pkcsep11_session=no fi fi -if test "x$enable_pkcsep11_session" != "xno" -a "x$with_zcrypt" != "xno"; then +if test "x$enable_pkcsep11_session" != "xno" -a "x$enable_ep11tok" = "xyes"; then enable_pkcsep11_session=yes else enable_pkcsep11_session=no @@ -662,12 +587,23 @@ fi AM_CONDITIONAL([ENABLE_LOCKS], [test "x$enable_locks" = "xyes"]) +dnl --- enable_md2 +if test "x$enable_md2" = "xyes"; then + enable_md2=yes +else + enable_md2=no + CFLAGS="$CFLAGS -DNOMD2" +fi +AM_CONDITIONAL([ENABLE_MD2], [test "x$enable_md2" = "xyes"]) + CFLAGS="$CFLAGS -DPKCS64 -D_XOPEN_SOURCE=600 -Wall -Wextra" CFLAGS+=' -DCONFIG_PATH=\"$(localstatedir)/lib/opencryptoki\" -DSBIN_PATH=\"$(sbindir)\" -DLIB_PATH=\"$(libdir)\" -DLOCKDIR_PATH=\"$(lockdir)\" -DOCK_CONFDIR=\"$(sysconfdir)/opencryptoki\" -DOCK_LOGDIR=\"$(logdir)\"' +CFLAGS+=" -std=c99 -Werror=implicit-int -Werror=implicit-function-declaration -Werror=int-conversion -Werror=strict-prototypes -Werror=old-style-definition -pedantic" # At this point, CFLAGS is set to something sensible AC_PROG_CC +AX_PROG_CC_FOR_BUILD AC_PROG_CXX # AC_PROG_CXX will return "g++" even if no c++ compiler is installed. # Check for that case, and issue an error if so. @@ -682,6 +618,7 @@ AC_CONFIG_MACRO_DIRS([m4]) AC_CONFIG_FILES([Makefile \ + misc/opencryptoki.pc \ usr/lib/api/shrd_mem.c \ man/man1/pkcsconf.1 \ man/man1/pkcsicsf.1 \ diff -Nru opencryptoki-3.18.0+dfsg/COPYRIGHTS opencryptoki-3.20.0+dfsg/COPYRIGHTS --- opencryptoki-3.18.0+dfsg/COPYRIGHTS 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/COPYRIGHTS 2023-02-13 09:22:42.000000000 +0100 @@ -1,6 +1,6 @@ Base openCryptoki Code and IBM submissions -(C) COPYRIGHT International Business Machines Corp. 2001, 2006 +(C) COPYRIGHT International Business Machines Corp. 2001, 2022 diff -Nru opencryptoki-3.18.0+dfsg/debian/changelog opencryptoki-3.20.0+dfsg/debian/changelog --- opencryptoki-3.18.0+dfsg/debian/changelog 2022-12-15 20:52:07.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/debian/changelog 2023-02-13 10:10:45.000000000 +0100 @@ -1,3 +1,36 @@ +opencryptoki (3.20.0+dfsg-0ubuntu1) lunar; urgency=medium + + * New upstream release (LP: #2003847), includes support for: + - ep11 token: master key consistency (LP: #2003629) + - ica and soft tokens: PKCS #11 3.0 - support AES_XTS (LP: #2003630) + - ep11 token: PKCS #11 3.0 - support AES_XTS (LP: #2003632) + - Support of ep11 token for new IBM Z Hardware (IBM z16) (LP: #2003635) + - ep11 token: vendor specific key derivation (LP: #2003638) + - key gen. with expected MKVP only on CCA and EP11 tokens (LP: #2003639) + - p11sak support Dilithium and Kyber keys (LP: #2003669) + * Remove patch + d/p/lp-1982842-EP11-Fix-C_GetMechanismList-returning-CKR_BUFFER_TOO.patch + since it's included in 3.19 and newer. + * Remove patch + d/p/lp-1989558-common-fix-memory-leak-in-save_private_token_object.patch + since it's included in 3.19 and newer. + * Adjust patch d/p/01-disable-testcases.patch due to minor change in context. + * Refresh patch d/p/03-dlopen-soname.patch to fix 'fuzz'. + * Modified patch + d/p/lp-1982842-move-pkcs11-group-assigment-from-makefile-to-postinst.patch + due to change in context, refresh it to fix 'fuzz' and remove addgroup + from Makefile.am, since this is handled in d/opencryptoki.postinst. + * Add opencryptoki.pc to d/libopencryptoki-dev.install. + * Add new config file ccatok.conf to d/opencryptoki.install.s390x. + * Consolidate multiple /etc/opencryptoki/*.conf entries in + d/opencryptoki.install to one line and make it more generic. + * Migrate in d/rules from 'dh_install --fail-missing --sourcedir=debian/tmp' + to 'dh_install --sourcedir=debian/tmp' and 'dh_missing --fail-missing'. + * Update 'Standards-Version' field in d/control to latest version 4.6.1.0. + * Expand the copyright year range in d/copyright relfecting the latest code. + + -- Frank Heimes Mon, 13 Feb 2023 10:10:45 +0100 + opencryptoki (3.18.0+dfsg-0ubuntu3) lunar; urgency=medium * No-change rebuild against libldap-2 diff -Nru opencryptoki-3.18.0+dfsg/debian/control opencryptoki-3.20.0+dfsg/debian/control --- opencryptoki-3.18.0+dfsg/debian/control 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/control 2023-02-13 10:10:45.000000000 +0100 @@ -15,7 +15,7 @@ libica-dev [s390x], libldap2-dev, libudev-dev -Standards-Version: 4.1.1 +Standards-Version: 4.6.1.0 Homepage: https://github.com/opencryptoki/opencryptoki Package: opencryptoki diff -Nru opencryptoki-3.18.0+dfsg/debian/libopencryptoki-dev.install opencryptoki-3.20.0+dfsg/debian/libopencryptoki-dev.install --- opencryptoki-3.18.0+dfsg/debian/libopencryptoki-dev.install 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/libopencryptoki-dev.install 2023-02-13 10:10:45.000000000 +0100 @@ -2,4 +2,5 @@ /usr/include/* /usr/include/opencryptoki/* /usr/lib/${DEB_HOST_MULTIARCH}/opencryptoki/*.so +/usr/lib/${DEB_HOST_MULTIARCH}/pkgconfig/*.pc diff -Nru opencryptoki-3.18.0+dfsg/debian/opencryptoki.install opencryptoki-3.20.0+dfsg/debian/opencryptoki.install --- opencryptoki-3.18.0+dfsg/debian/opencryptoki.install 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/opencryptoki.install 2023-02-13 10:10:45.000000000 +0100 @@ -5,7 +5,5 @@ /usr/lib/${DEB_HOST_MULTIARCH}/opencryptoki/stdll/*.so /usr/lib/tmpfiles.d/opencryptoki.conf /var/lib/opencryptoki -/etc/opencryptoki/opencryptoki.conf -/etc/opencryptoki/p11sak_defined_attrs.conf -/etc/opencryptoki/strength.conf +/etc/opencryptoki /lib/systemd/system/pkcsslotd.service diff -Nru opencryptoki-3.18.0+dfsg/debian/opencryptoki.install.s390x opencryptoki-3.20.0+dfsg/debian/opencryptoki.install.s390x --- opencryptoki-3.18.0+dfsg/debian/opencryptoki.install.s390x 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/opencryptoki.install.s390x 2023-02-13 10:10:45.000000000 +0100 @@ -11,3 +11,4 @@ /lib/systemd/system/pkcsslotd.service /etc/opencryptoki/ep11tok.conf /etc/opencryptoki/ep11cpfilter.conf +/etc/opencryptoki/ccatok.conf diff -Nru opencryptoki-3.18.0+dfsg/debian/patches/01-disable-testcases.patch opencryptoki-3.20.0+dfsg/debian/patches/01-disable-testcases.patch --- opencryptoki-3.18.0+dfsg/debian/patches/01-disable-testcases.patch 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/patches/01-disable-testcases.patch 2023-02-13 10:10:45.000000000 +0100 @@ -8,7 +8,7 @@ @@ -1,7 +1,7 @@ dnl Process this file with autoconf to produce a configure script. AC_PREREQ([2.69]) - AC_INIT([openCryptoki],[3.18.0],[https://github.com/opencryptoki/opencryptoki/issues],[],[https://github.com/opencryptoki/opencryptoki]) + AC_INIT([openCryptoki],[3.20.0],[https://github.com/opencryptoki/opencryptoki/issues],[],[https://github.com/opencryptoki/opencryptoki]) -AC_CONFIG_SRCDIR([testcases/common/common.c]) +AC_CONFIG_SRCDIR([usr/include/pkcs11.h]) diff -Nru opencryptoki-3.18.0+dfsg/debian/patches/03-dlopen-soname.patch opencryptoki-3.20.0+dfsg/debian/patches/03-dlopen-soname.patch --- opencryptoki-3.18.0+dfsg/debian/patches/03-dlopen-soname.patch 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/patches/03-dlopen-soname.patch 2023-02-13 10:10:45.000000000 +0100 @@ -4,9 +4,9 @@ --- a/usr/sbin/pkcscca/pkcscca.c +++ b/usr/sbin/pkcscca/pkcscca.c -@@ -592,7 +592,7 @@ +@@ -649,7 +649,7 @@ CK_RV rv; - CK_RV (*pfoo) (); + CK_RV (*getfunclist)(CK_FUNCTION_LIST_PTR_PTR ppFunctionList); char *loc1_lib = "/usr/lib/pkcs11/PKCS11_API.so64"; - char *loc2_lib = "libopencryptoki.so"; + char *loc2_lib = "libopencryptoki.so.0"; @@ -15,19 +15,19 @@ --- a/usr/sbin/pkcsconf/pkcsconf.c +++ b/usr/sbin/pkcsconf/pkcsconf.c -@@ -1134,7 +1134,7 @@ +@@ -969,7 +969,7 @@ * error */ /* The host machine should have the right library in the * LD_LIBRARY_PATH */ - dllPtr = dlopen("libopencryptoki.so", RTLD_NOW); + dllPtr = dlopen("libopencryptoki.so.0", RTLD_NOW); if (!dllPtr) { - printf("Error loading PKCS#11 library\n"); - printf("dlopen error: %s\n", dlerror()); + warnx("Error loading PKCS#11 library"); + warnx("dlopen error: %s", dlerror()); --- a/usr/sbin/pkcsep11_migrate/pkcsep11_migrate.c +++ b/usr/sbin/pkcsep11_migrate/pkcsep11_migrate.c -@@ -366,7 +366,7 @@ - CK_RV (*func_list) () = NULL; +@@ -345,7 +345,7 @@ + CK_RV (*func_list)(CK_FUNCTION_LIST_PTR_PTR ppFunctionList) = NULL; void *d; char *evar; - char *evar_default = "libopencryptoki.so"; @@ -37,8 +37,8 @@ if (evar == NULL) { --- a/usr/sbin/pkcsep11_session/pkcsep11_session.c +++ b/usr/sbin/pkcsep11_session/pkcsep11_session.c -@@ -212,7 +212,7 @@ - CK_RV (*func_list)() = NULL; +@@ -156,7 +156,7 @@ + CK_RV (*func_list)(CK_FUNCTION_LIST_PTR_PTR ppFunctionList) = NULL; void *d; char *evar; - char *evar_default = "libopencryptoki.so"; diff -Nru opencryptoki-3.18.0+dfsg/debian/patches/lp-1982842-EP11-Fix-C_GetMechanismList-returning-CKR_BUFFER_TOO.patch opencryptoki-3.20.0+dfsg/debian/patches/lp-1982842-EP11-Fix-C_GetMechanismList-returning-CKR_BUFFER_TOO.patch --- opencryptoki-3.18.0+dfsg/debian/patches/lp-1982842-EP11-Fix-C_GetMechanismList-returning-CKR_BUFFER_TOO.patch 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/patches/lp-1982842-EP11-Fix-C_GetMechanismList-returning-CKR_BUFFER_TOO.patch 1970-01-01 01:00:00.000000000 +0100 @@ -1,42 +0,0 @@ -From b545050b338e46c29936a2748aab7200e69a5c91 Mon Sep 17 00:00:00 2001 -From: Ingo Franzki -Date: Tue, 26 Jul 2022 15:11:06 +0200 -Subject: [PATCH] EP11: Fix C_GetMechanismList returning CKR_BUFFER_TOO_SMALL - -For mixed card levels, the size query call and the call to obtain the -list may run on different cards. When the size query call runs on a -card with less mechanisms than the second call, will fail, but it -returns the larger larger number of mechanisms. - -The code already re-allocates the buffer for retrieving the mechanism -list, but does not return the larger number in pulCount. This will -lead to a CKR_BUFFER_TOO_SMALL when the application calls C_GetMechanismList -again to obtain the list of mechanisms, because the applications buffer -is too small. - -Signed-off-by: Ingo Franzki - -Origin: upstream, https://github.com/opencryptoki/opencryptoki/commit/b545050b338e46c29936a2748aab7200e69a5c91 -Bug-Ubuntu: https://bugs.launchpad.net/bugs/1982842 -Last-Update: 2022-08-15 - ---- - usr/lib/ep11_stdll/ep11_specific.c | 2 ++ - 1 file changed, 2 insertions(+) - -diff --git a/usr/lib/ep11_stdll/ep11_specific.c b/usr/lib/ep11_stdll/ep11_specific.c -index 8d796452..1629e664 100644 ---- a/usr/lib/ep11_stdll/ep11_specific.c -+++ b/usr/lib/ep11_stdll/ep11_specific.c -@@ -8977,6 +8977,8 @@ CK_RV ep11tok_get_mechanism_list(STDLL_TokData_t * tokdata, - if (rc != CKR_BUFFER_TOO_SMALL) - goto out; - } -+ /* counter was updated in case of CKR_BUFFER_TOO_SMALL */ -+ *pulCount = counter; - } while (rc == CKR_BUFFER_TOO_SMALL); - - for (i = 0; i < counter; i++) { --- -2.25.1 - diff -Nru opencryptoki-3.18.0+dfsg/debian/patches/lp-1982842-move-pkcs11-group-assigment-from-makefile-to-postinst.patch opencryptoki-3.20.0+dfsg/debian/patches/lp-1982842-move-pkcs11-group-assigment-from-makefile-to-postinst.patch --- opencryptoki-3.18.0+dfsg/debian/patches/lp-1982842-move-pkcs11-group-assigment-from-makefile-to-postinst.patch 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/patches/lp-1982842-move-pkcs11-group-assigment-from-makefile-to-postinst.patch 2023-02-13 10:10:45.000000000 +0100 @@ -14,7 +14,15 @@ This patch header follows DEP-3: http://dep.debian.net/deps/dep3/ --- a/Makefile.am +++ b/Makefile.am -@@ -78,7 +78,7 @@ +@@ -36,7 +36,6 @@ + include doc/doc.mk + + install-data-hook: +- getent group pkcs11 > /dev/null || $(GROUPADD) -r pkcs11 + if ENABLE_LIBRARY + $(MKDIR_P) $(DESTDIR)$(libdir)/opencryptoki/stdll + $(MKDIR_P) $(DESTDIR)$(libdir)/pkcs11 +@@ -84,7 +83,7 @@ endif if ENABLE_P11SAK test -f $(DESTDIR)$(sysconfdir)/opencryptoki || $(MKDIR_P) $(DESTDIR)$(sysconfdir)/opencryptoki || true @@ -23,12 +31,12 @@ endif if ENABLE_ICATOK cd $(DESTDIR)$(libdir)/opencryptoki/stdll && \ -@@ -129,7 +129,7 @@ +@@ -135,7 +134,7 @@ if ENABLE_DAEMON test -f $(DESTDIR)$(sysconfdir)/opencryptoki || $(MKDIR_P) $(DESTDIR)$(sysconfdir)/opencryptoki || true test -f $(DESTDIR)$(sysconfdir)/opencryptoki/opencryptoki.conf || $(INSTALL) -m 644 $(srcdir)/usr/sbin/pkcsslotd/opencryptoki.conf $(DESTDIR)$(sysconfdir)/opencryptoki/opencryptoki.conf || true - test -f $(DESTDIR)$(sysconfdir)/opencryptoki/strength.conf || $(INSTALL) -m 640 -o root -g pkcs11 -T $(srcdir)/doc/strength-example.conf $(DESTDIR)$(sysconfdir)/opencryptoki/strength.conf || true + test -f $(DESTDIR)$(sysconfdir)/opencryptoki/strength.conf || $(INSTALL) -m 640 -o root -T $(srcdir)/doc/strength-example.conf $(DESTDIR)$(sysconfdir)/opencryptoki/strength.conf || true - if ENABLE_SYSTEMD - mkdir -p $(DESTDIR)/usr/lib/tmpfiles.d - cp $(srcdir)/misc/tmpfiles.conf $(DESTDIR)/usr/lib/tmpfiles.d/opencryptoki.conf + endif + $(MKDIR_P) $(DESTDIR)/etc/ld.so.conf.d + echo "$(libdir)/opencryptoki" >\ diff -Nru opencryptoki-3.18.0+dfsg/debian/patches/lp-1989558-common-fix-memory-leak-in-save_private_token_object.patch opencryptoki-3.20.0+dfsg/debian/patches/lp-1989558-common-fix-memory-leak-in-save_private_token_object.patch --- opencryptoki-3.18.0+dfsg/debian/patches/lp-1989558-common-fix-memory-leak-in-save_private_token_object.patch 2022-09-14 15:01:02.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/patches/lp-1989558-common-fix-memory-leak-in-save_private_token_object.patch 1970-01-01 01:00:00.000000000 +0100 @@ -1,43 +0,0 @@ -From d5ccb00e52f5b0c66533f085cda36f63f7583d44 Mon Sep 17 00:00:00 2001 -From: Ingo Franzki -Date: Tue, 19 Jul 2022 16:16:55 +0200 -Subject: [PATCH] common: fix memory leak in save_private_token_object - -Reported by coverty scan: - -Error: RESOURCE_LEAK (CWE-772): -opencryptoki-3.18.0/usr/lib/common/loadsave.c:2311: alloc_fn: -Storage is returned from allocation function "fopen". -opencryptoki-3.18.0/usr/lib/common/loadsave.c:2311: var_assign: -Assigning: "fp" = storage returned from "fopen(fname, "r")". -opencryptoki-3.18.0/usr/lib/common/loadsave.c:2316: noescape: -Resource "fp" is not freed or pointed-to in "fileno". -opencryptoki-3.18.0/usr/lib/common/loadsave.c:2407: overwrite_var: -Overwriting "fp" in "fp = fopen(fname, "w")" leaks the storage that "fp" points to. - -Signed-off-by: Ingo Franzki - -Origin: upstream, https://github.com/opencryptoki/opencryptoki/commit/d5ccb00e52f5b0c66533f085cda36f63f7583d44 -Bug-Ubuntu: https://bugs.launchpad.net/bugs/1989558 -Last-Update: 2022-09-14 - ---- - usr/lib/common/loadsave.c | 2 ++ - 1 file changed, 2 insertions(+) - -diff --git a/usr/lib/common/loadsave.c b/usr/lib/common/loadsave.c -index bbd691c0..91955f47 100644 ---- a/usr/lib/common/loadsave.c -+++ b/usr/lib/common/loadsave.c -@@ -2344,6 +2344,8 @@ CK_RV save_private_token_object(STDLL_TokData_t *tokdata, OBJECT *obj) - /* New token objects files created by mkstemp have a size of zero */ - if (sb.st_size == 0) { - new = 1; -+ fclose(fp); -+ fp = NULL; - goto do_work; - } - --- -2.25.1 - diff -Nru opencryptoki-3.18.0+dfsg/debian/patches/series opencryptoki-3.20.0+dfsg/debian/patches/series --- opencryptoki-3.18.0+dfsg/debian/patches/series 2022-09-14 15:01:02.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/patches/series 2023-02-13 10:10:45.000000000 +0100 @@ -2,6 +2,4 @@ 03-dlopen-soname.patch 04-pkcsslotd-cmdline-args.patch -lp-1982842-EP11-Fix-C_GetMechanismList-returning-CKR_BUFFER_TOO.patch lp-1982842-move-pkcs11-group-assigment-from-makefile-to-postinst.patch -lp-1989558-common-fix-memory-leak-in-save_private_token_object.patch diff -Nru opencryptoki-3.18.0+dfsg/debian/rules opencryptoki-3.20.0+dfsg/debian/rules --- opencryptoki-3.18.0+dfsg/debian/rules 2022-08-15 12:29:35.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/debian/rules 2023-02-13 10:10:45.000000000 +0100 @@ -40,7 +40,8 @@ rm -f debian/tmp/lib/systemd/system/tmpfiles.conf override_dh_install: - dh_install --fail-missing --sourcedir=debian/tmp + dh_install --sourcedir=debian/tmp + dh_missing --list-missing override_dh_installinit: dh_installinit -p opencryptoki --name pkcsslotd diff -Nru opencryptoki-3.18.0+dfsg/doc/doc.mk opencryptoki-3.20.0+dfsg/doc/doc.mk --- opencryptoki-3.18.0+dfsg/doc/doc.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/doc/doc.mk 2023-02-13 09:22:42.000000000 +0100 @@ -5,3 +5,4 @@ $(AM_V_GEN) $(MKDIR_P) doc && tools/policyexamplegen > doc/policy-example.conf EXTRA_DIST += $(doc_DATA) +CLEANFILES += doc/policy-example.conf diff -Nru opencryptoki-3.18.0+dfsg/.gitignore opencryptoki-3.20.0+dfsg/.gitignore --- opencryptoki-3.18.0+dfsg/.gitignore 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/.gitignore 2023-02-13 09:22:42.000000000 +0100 @@ -1,440 +1,237 @@ -Makefile.in -aclocal.m4 -autom4te.cache -compile -config.guess -config.sub -configure -depcomp -install-sh -ltmain.sh -m4/libtool.m4 -m4/ltoptions.m4 -m4/ltsugar.m4 -m4/ltversion.m4 -m4/lt~obsolete.m4 -missing -ylwrap - - -Makefile -config.log -config.status -libtool -man/man1/pkcscca.1 -man/man1/pkcsconf.1 -man/man1/pkcsep11_migrate.1 -man/man1/pkcsep11_session.1 -man/man1/pkcsicsf.1 -man/man1/p11sak.1 -man/man5/opencryptoki.conf.5 -man/man7/opencryptoki.7 -man/man8/pkcsslotd.8 -testcases/common/.deps/ -testcases/crypto/.deps/ -testcases/login/.deps/ -testcases/misc_tests/.deps/ -testcases/pkcs11/.deps/ -usr/lib/api/.deps/ -usr/lib/api/shrd_mem.c -usr/lib/cca_stdll/.deps/ -usr/lib/common/.deps/ -usr/lib/ep11_stdll/.deps/ -usr/lib/ica_s390_stdll/.deps/ -usr/lib/icsf_stdll/.deps/ -usr/lib/soft_stdll/.deps/ -usr/lib/tpm_stdll/.deps/ -usr/sbin/pkcscca/.deps/ -usr/sbin/pkcsconf/.deps/ -usr/sbin/pkcsep11_migrate/.deps/ -usr/sbin/pkcsep11_session/.deps/ -usr/sbin/pkcsicsf/.deps/ -usr/sbin/pkcsslotd/.deps/ -usr/sbin/p11sak/.deps/ -usr/sbin/pkcstok_migrate/.deps/ - - -misc/pkcsslotd -opencryptoki/ -testcases/common/.dirstamp -testcases/common/.libs/ -testcases/common/libcommon.la -testcases/common/testcases_common_libcommon_la-common.lo -testcases/crypto/.dirstamp +# COPYRIGHT (c) International Business Machines Corp. 2001-2022 +# +# This program is provided under the terms of the Common Public License, +# version 1.0 (CPL-1.0). Any use, reproduction or distribution for this software +# constitutes recipient's acceptance of CPL-1.0 terms which can be found +# in the file LICENSE file or at https://opensource.org/licenses/cpl1.0.php +# +# project specific ignore patterns +# ignore executables +testcases/build/cpp_test +testcases/crypto/ab_tests testcases/crypto/aes_tests testcases/crypto/des3_tests testcases/crypto/des_tests testcases/crypto/dh_tests testcases/crypto/digest_tests +testcases/crypto/dilithium_tests testcases/crypto/dsa_tests testcases/crypto/ec_tests testcases/crypto/rsa_tests testcases/crypto/rsaupdate_tests testcases/crypto/ssl3_tests -testcases/crypto/testcases_crypto_aes_tests-aes_func.o -testcases/crypto/testcases_crypto_des3_tests-des3_func.o -testcases/crypto/testcases_crypto_des_tests-des_func.o -testcases/crypto/testcases_crypto_dh_tests-dh_func.o -testcases/crypto/testcases_crypto_digest_tests-digest_func.o -testcases/crypto/testcases_crypto_dsa_tests-dsa_func.o -testcases/crypto/testcases_crypto_ec_tests-ec_func.o -testcases/crypto/testcases_crypto_rsa_tests-rsa_func.o -testcases/crypto/testcases_crypto_rsaupdate_tests-rsaupdate_func.o -testcases/crypto/testcases_crypto_ssl3_tests-ssl3_func.o +testcases/crypto/kyber_tests testcases/init_token.sh -testcases/log-slot_*.txt -testcases/login/.dirstamp testcases/login/digest_init testcases/login/init_pin testcases/login/init_tok testcases/login/login testcases/login/login_flags_test testcases/login/set_pin -testcases/login/testcases_login_digest_init-digest_init.o -testcases/login/testcases_login_init_pin-init_pin.o -testcases/login/testcases_login_init_tok-init_tok.o -testcases/login/testcases_login_login-login.o -testcases/login/testcases_login_login_flags_test-login_flags.o -testcases/login/testcases_login_set_pin-set_pin.o -testcases/misc_tests/.dirstamp +testcases/misc_tests/cca_export_import_test +testcases/misc_tests/events +testcases/misc_tests/fork +testcases/misc_tests/multi_instance +testcases/misc_tests/obj_lock testcases/misc_tests/obj_mgmt_lock_tests testcases/misc_tests/obj_mgmt_tests +testcases/misc_tests/reencrypt testcases/misc_tests/speed -testcases/misc_tests/testcases_misc_tests_obj_mgmt_lock_tests-obj_mgmt_lock.o -testcases/misc_tests/testcases_misc_tests_obj_mgmt_tests-obj_mgmt.o -testcases/misc_tests/testcases_misc_tests_speed-speed.o -testcases/misc_tests/testcases_misc_tests_threadmkobj-threadmkobj.o -testcases/misc_tests/testcases_misc_tests_tok_des-tok_des.o -testcases/misc_tests/testcases_misc_tests_tok_obj-tok_obj.o -testcases/misc_tests/testcases_misc_tests_tok_rsa-tok_rsa.o testcases/misc_tests/threadmkobj +testcases/misc_tests/tok2tok_transport testcases/misc_tests/tok_des testcases/misc_tests/tok_obj testcases/misc_tests/tok_rsa +testcases/misc_tests/dual_functions testcases/ock_tests.sh -testcases/pkcs11/.dirstamp testcases/pkcs11/attribute testcases/pkcs11/copyobjects testcases/pkcs11/destroyobjects testcases/pkcs11/findobjects testcases/pkcs11/gen_purpose testcases/pkcs11/generate_keypair +testcases/pkcs11/get_interface testcases/pkcs11/getobjectsize testcases/pkcs11/hw_fn testcases/pkcs11/sess_bench testcases/pkcs11/sess_mgmt_tests testcases/pkcs11/sess_opstate -testcases/pkcs11/testcases_pkcs11_attribute-attribute.o -testcases/pkcs11/testcases_pkcs11_copyobjects-copyobjects.o -testcases/pkcs11/testcases_pkcs11_destroyobjects-destroyobjects.o -testcases/pkcs11/testcases_pkcs11_findobjects-findobjects.o -testcases/pkcs11/testcases_pkcs11_gen_purpose-gen_purpose.o -testcases/pkcs11/testcases_pkcs11_generate_keypair-generate_keypair.o -testcases/pkcs11/testcases_pkcs11_getobjectsize-getobjectsize.o -testcases/pkcs11/testcases_pkcs11_hw_fn-hw_fn.o -testcases/pkcs11/testcases_pkcs11_sess_bench-sess_perf.o -testcases/pkcs11/testcases_pkcs11_sess_mgmt_tests-sess_mgmt.o -testcases/pkcs11/testcases_pkcs11_sess_opstate-sess_opstate.o -usr/lib/api/.dirstamp -usr/lib/api/.libs/ -usr/lib/api/opencryptoki_libopencryptoki_la-api_interface.lo -usr/lib/api/opencryptoki_libopencryptoki_la-apiutil.lo -usr/lib/api/opencryptoki_libopencryptoki_la-shrd_mem.lo -usr/lib/api/opencryptoki_libopencryptoki_la-socket_client.lo -usr/lib/cca_stdll/.dirstamp -usr/lib/cca_stdll/.libs/ -usr/lib/cca_stdll/opencryptoki_stdll_libpkcs11_cca_la-cca_specific.lo -usr/lib/common/.dirstamp -usr/lib/common/.libs/ -usr/lib/common/opencryptoki_libopencryptoki_la-lock_btree.lo -usr/lib/common/opencryptoki_libopencryptoki_la-trace.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-asn1.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-cert.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-data_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-decr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-dig_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-dp_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-encr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-globals.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-hwf_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-key.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-key_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-loadsave.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-lock_btree.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-lock_sess_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_aes.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_des.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_des3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_dh.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_ec.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_list.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_md2.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_md5.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_rng.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_rsa.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_sha.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-mech_ssl3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-new_host.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-obj_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-object.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-p11util.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-shared_memory.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-sign_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-sw_crypt.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-template.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-trace.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-utility.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_cca_la-verify_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-asn1.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-attributes.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-cert.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-data_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-decr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-dig_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-dp_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-encr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-globals.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-hwf_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-key.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-key_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-loadsave.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-lock_btree.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-lock_sess_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_aes.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_des.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_des3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_dh.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_dsa.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_ec.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_list.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_md2.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_md5.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_rng.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_rsa.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_sha.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-mech_ssl3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-obj_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-object.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-p11util.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-shared_memory.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-sign_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-sw_crypt.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-template.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-trace.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-utility.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ep11_la-verify_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-asn1.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-cert.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-data_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-decr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-dig_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-dp_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-encr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-globals.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-hwf_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-key.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-key_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-loadsave.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-lock_btree.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-lock_sess_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_aes.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_des.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_des3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_ec.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_list.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_md2.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_md5.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_rng.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_rsa.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_sha.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-mech_ssl3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-new_host.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-obj_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-object.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-p11util.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-shared_memory.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-sign_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-sw_crypt.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-template.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-trace.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-utility.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_ica_la-verify_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-asn1.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-attributes.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-cert.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-data_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-decr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-dig_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-dp_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-encr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-globals.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-hwf_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-key.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-key_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-loadsave.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-lock_btree.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-lock_sess_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_aes.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_des.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_des3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_dh.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_ec.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_list.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_md2.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_md5.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_rng.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_rsa.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_sha.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-mech_ssl3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-obj_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-object.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-p11util.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-shared_memory.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-sign_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-sw_crypt.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-template.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-trace.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-utility.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_icsf_la-verify_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-asn1.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-cert.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-data_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-decr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-dig_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-dp_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-encr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-globals.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-hwf_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-key.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-key_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-loadsave.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-lock_btree.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-lock_sess_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_aes.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_des.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_des3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_dh.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_ec.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_list.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_md2.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_md5.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_rng.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_rsa.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_sha.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-mech_ssl3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-new_host.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-obj_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-object.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-p11util.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-shared_memory.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-sign_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-sw_crypt.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-template.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-trace.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-utility.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_sw_la-verify_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-asn1.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-cert.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-data_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-decr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-dig_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-dp_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-encr_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-globals.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-hwf_obj.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-key.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-key_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-loadsave.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-lock_btree.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-lock_sess_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_aes.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_des.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_des3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_dh.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_ec.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_list.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_md2.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_md5.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_rng.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_rsa.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_sha.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-mech_ssl3.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-new_host.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-obj_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-object.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-p11util.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-shared_memory.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-sign_mgr.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-sw_crypt.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-template.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-trace.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-utility.lo -usr/lib/common/opencryptoki_stdll_libpkcs11_tpm_la-verify_mgr.lo -usr/lib/common/testcases_common_libcommon_la-p11util.lo -usr/lib/common/testcases_crypto_aes_tests-p11util.o -usr/lib/common/testcases_login_login-p11util.o -usr/lib/common/testcases_login_login_flags_test-p11util.o -usr/lib/common/testcases_misc_tests_speed-p11util.o -usr/lib/common/testcases_misc_tests_threadmkobj-p11util.o -usr/lib/common/testcases_misc_tests_tok_obj-p11util.o -usr/lib/common/usr_sbin_pkcscca_pkcscca-p11util.o -usr/lib/common/usr_sbin_pkcscca_pkcscca-sw_crypt.o -usr/lib/common/usr_sbin_pkcscca_pkcscca-trace.o -usr/lib/common/usr_sbin_pkcsconf_pkcsconf-p11util.o -usr/lib/common/usr_sbin_pkcsep11_migrate_pkcsep11_migrate-p11util.o -usr/lib/common/usr_sbin_pkcsep11_session_pkcsep11_session-p11util.o -usr/lib/common/usr_sbin_pkcsicsf_pkcsicsf-trace.o -usr/lib/ep11_stdll/.dirstamp -usr/lib/ep11_stdll/.libs/ -usr/lib/ep11_stdll/opencryptoki_stdll_libpkcs11_ep11_la-ep11_specific.lo -usr/lib/ep11_stdll/opencryptoki_stdll_libpkcs11_ep11_la-new_host.lo -usr/lib/ica_s390_stdll/.dirstamp -usr/lib/ica_s390_stdll/.libs/ -usr/lib/ica_s390_stdll/opencryptoki_stdll_libpkcs11_ica_la-ica_specific.lo -usr/lib/icsf_stdll/.dirstamp -usr/lib/icsf_stdll/.libs/ -usr/lib/icsf_stdll/opencryptoki_stdll_libpkcs11_icsf_la-icsf.lo -usr/lib/icsf_stdll/opencryptoki_stdll_libpkcs11_icsf_la-icsf_specific.lo -usr/lib/icsf_stdll/opencryptoki_stdll_libpkcs11_icsf_la-new_host.lo -usr/lib/icsf_stdll/opencryptoki_stdll_libpkcs11_icsf_la-pbkdf.lo -usr/lib/icsf_stdll/usr_sbin_pkcsicsf_pkcsicsf-icsf.o -usr/lib/icsf_stdll/usr_sbin_pkcsicsf_pkcsicsf-pbkdf.o -usr/lib/soft_stdll/.dirstamp -usr/lib/soft_stdll/.libs/ -usr/lib/soft_stdll/opencryptoki_stdll_libpkcs11_sw_la-soft_specific.lo -usr/lib/tpm_stdll/.dirstamp -usr/lib/tpm_stdll/.libs/ -usr/lib/tpm_stdll/opencryptoki_stdll_libpkcs11_tpm_la-tpm_openssl.lo -usr/lib/tpm_stdll/opencryptoki_stdll_libpkcs11_tpm_la-tpm_specific.lo -usr/lib/tpm_stdll/opencryptoki_stdll_libpkcs11_tpm_la-tpm_util.lo -usr/sbin/pkcscca/.dirstamp +testcases/policy/policytest +testcases/policy/policytest.sh +testcases/unit/configdump +testcases/unit/hashmaptest +testcases/unit/mechtabletest +testcases/unit/policytest +testcases/unit/buffertest +testcases/unit/uritest +testcases/unit/pintest +usr/sbin/p11sak/p11sak usr/sbin/pkcscca/pkcscca -usr/sbin/pkcscca/usr_sbin_pkcscca_pkcscca-pkcscca.o -usr/sbin/pkcsconf/.dirstamp usr/sbin/pkcsconf/pkcsconf -usr/sbin/pkcsconf/usr_sbin_pkcsconf_pkcsconf-pkcsconf.o -usr/sbin/pkcsep11_migrate/.dirstamp -usr/sbin/pkcsep11_migrate/pkcsep11_migrate -usr/sbin/pkcsep11_migrate/usr_sbin_pkcsep11_migrate_pkcsep11_migrate-pkcsep11_migrate.o -usr/sbin/pkcsep11_session/.dirstamp -usr/sbin/pkcsep11_session/pkcsep11_session -usr/sbin/pkcsep11_session/usr_sbin_pkcsep11_session_pkcsep11_session-pkcsep11_session.o -usr/sbin/pkcsicsf/.dirstamp usr/sbin/pkcsicsf/pkcsicsf -usr/sbin/pkcsicsf/usr_sbin_pkcsicsf_pkcsicsf-pkcsicsf.o -usr/sbin/pkcsslotd/.dirstamp usr/sbin/pkcsslotd/pkcsslotd -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-daemon.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-err.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-garbage_linux.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-log.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-mutex.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-pkcsslotd_util.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-shmem.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-signal.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-slotmgr.o -usr/sbin/pkcsslotd/usr_sbin_pkcsslotd_pkcsslotd-socket_server.o -usr/sbin/p11sak/.dirstamp -usr/sbin/p11sak/p11sak -usr/sbin/p11sak/usr_sbin_p11sak_p11sak-p11sak.o -usr/sbin/pkcstok_migrate/.dirstamp \ No newline at end of file +usr/sbin/pkcsstats/pkcsstats +usr/sbin/pkcstok_migrate/pkcstok_migrate +usr/sbin/pkcsep11_migrate/pkcsep11_migrate +usr/sbin/pkcsep11_session/pkcsep11_session +tools/policyexamplegen +tools/tableidxgen + +# ignore test logs +*.log +*.trs + +# ignore build stubs +*.lai +libtool + +# ignore generated source (from .in) +usr/lib/api/shrd_mem.c +man/man1/p11sak.1 +man/man1/pkcsep11_session.1 +man/man1/pkcsicsf.1 +man/man1/pkcstok_migrate.1 +man/man1/pkcsep11_migrate.1 +man/man1/pkcscca.1 +man/man1/pkcsconf.1 +man/man1/pkcsstats.1 +man/man5/policy.conf.5 +man/man5/p11sak_defined_attrs.conf.5 +man/man5/opencryptoki.conf.5 +man/man5/strength.conf.5 +man/man8/pkcsslotd.8 +man/man7/opencryptoki.7 +misc/opencryptoki.conf +misc/pkcsslotd.service +misc/pkcsslotd +misc/opencryptoki.pc +testcases/init_vhsm.exp +testcases/policy/policytest.sh +testcases/ock_tests.sh +testcases/cleanup_vhsm.exp +testcases/init_token.sh + +# ignore generated source (other) +doc/policy-example.conf +usr/lib/api/mechtable-gen.h +usr/lib/api/mechtable.c +usr/lib/api/mechtable.log +usr/lib/api/shrd_mem.c +usr/lib/config/cfglex.c +usr/lib/config/cfglex.h +usr/lib/config/cfgparse.c +usr/lib/config/cfgparse.h +usr/lib/config/cfgparse.output + +# common C ignores +*.d +*.o +*.obj +*.elf +*.ilk +*.map +*.exp +*.gch +*.pch +*.lib +*.a +*.la +*.lo +*.so +*.so.* +*.dylib +*.out +*.hex +*.dSYM/ +*.su +*.idb +*.pdb + +# common autotools ignores +Makefile.in +/ar-lib +/mdate-sh +/py-compile +/test-driver +/ylwrap +.deps/ +.dirstamp +autom4te.cache +/autoscan.log +/autoscan-*.log +/aclocal.m4 +/compile +/config.cache +/config.guess +/config.h.in +/config.log +/config.status +/config.sub +/configure +/configure.scan +/depcomp +/install-sh +/missing +/stamp-h1 +/ltmain.sh +/texinfo.tex +m4/libtool.m4 +m4/ltoptions.m4 +m4/ltsugar.m4 +m4/ltversion.m4 +m4/lt~obsolete.m4 +Makefile + +# common tag ignores +TAGS +.TAGS +!TAGS/ +tags +.tags +!tags/ +gtags.files +GTAGS +GRTAGS +GPATH +GSYMS +cscope.files +cscope.out +cscope.in.out +cscope.po.out + +# common emacs ignores +*~ +\#*\# +/.emacs.desktop +/.emacs.desktop.lock +*.elc +auto-save-list +tramp +.\#* +.org-id-locations +*_archive +*_flymake.* +/eshell/history +/eshell/lastdir +/elpa/ +*.rel +/auto/ +.cask/ +dist/ +flycheck_*.el +/server/ +.projectile +.dir-locals.el +/network-security.data + +# common vim ignores +[._]*.s[a-v][a-z] +[._]*.sw[a-p] +[._]s[a-rt-v][a-z] +[._]ss[a-gi-z] +[._]sw[a-p] +Session.vim +Sessionx.vim +.netrwhist +*~ +[._]*.un~ diff -Nru opencryptoki-3.18.0+dfsg/INSTALL opencryptoki-3.20.0+dfsg/INSTALL --- opencryptoki-3.18.0+dfsg/INSTALL 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/INSTALL 2023-02-13 09:22:42.000000000 +0100 @@ -96,6 +96,11 @@ you can use the `configure' options `--x-includes=DIR' and `--x-libraries=DIR' to specify their locations. + Note: Do not specify 'prefix=/foo/bar', 'libdir=/foo/bar' with +the 'make' invocation. Specify them with 'configure' instead. Specifying +them with 'make' is not supported by the openCryptoki package and may +produce unexpected results! + Specifying the System Type ========================== diff -Nru opencryptoki-3.18.0+dfsg/Makefile.am opencryptoki-3.20.0+dfsg/Makefile.am --- opencryptoki-3.18.0+dfsg/Makefile.am 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/Makefile.am 2023-02-13 09:22:42.000000000 +0100 @@ -1,6 +1,12 @@ ACLOCAL_AMFLAGS = -I m4 EXTRA_DIST = opencryptoki.map opencryptoki_tok.map CLEANFILES = +DISTCLEANFILES = *~ +MAINTAINERCLEANFILES = test-driver \ + Makefile.in aclocal.m4 compile configure config.guess \ + config.sub depcomp install-sh ltmain.sh m4/* missing \ + depcomp ylwrap + AM_YFLAGS = -d -v BUILT_SOURCES = @@ -33,6 +39,7 @@ include doc/doc.mk install-data-hook: + getent group pkcs11 > /dev/null || $(GROUPADD) -r pkcs11 if ENABLE_LIBRARY $(MKDIR_P) $(DESTDIR)$(libdir)/opencryptoki/stdll $(MKDIR_P) $(DESTDIR)$(libdir)/pkcs11 @@ -60,6 +67,8 @@ $(MKDIR_P) $(DESTDIR)$(lockdir)/ccatok $(CHGRP) pkcs11 $(DESTDIR)$(lockdir)/ccatok $(CHMOD) 0770 $(DESTDIR)$(lockdir)/ccatok + test -f $(DESTDIR)$(sysconfdir)/opencryptoki || $(MKDIR_P) $(DESTDIR)$(sysconfdir)/opencryptoki || true + test -f $(DESTDIR)$(sysconfdir)/opencryptoki/ccatok.conf || $(INSTALL) -m 644 $(srcdir)/usr/lib/cca_stdll/ccatok.conf $(DESTDIR)$(sysconfdir)/opencryptoki/ccatok.conf || true endif if ENABLE_EP11TOK cd $(DESTDIR)$(libdir)/opencryptoki/stdll && \ @@ -130,12 +139,6 @@ test -f $(DESTDIR)$(sysconfdir)/opencryptoki || $(MKDIR_P) $(DESTDIR)$(sysconfdir)/opencryptoki || true test -f $(DESTDIR)$(sysconfdir)/opencryptoki/opencryptoki.conf || $(INSTALL) -m 644 $(srcdir)/usr/sbin/pkcsslotd/opencryptoki.conf $(DESTDIR)$(sysconfdir)/opencryptoki/opencryptoki.conf || true test -f $(DESTDIR)$(sysconfdir)/opencryptoki/strength.conf || $(INSTALL) -m 640 -o root -g pkcs11 -T $(srcdir)/doc/strength-example.conf $(DESTDIR)$(sysconfdir)/opencryptoki/strength.conf || true -if ENABLE_SYSTEMD - mkdir -p $(DESTDIR)/usr/lib/tmpfiles.d - cp $(srcdir)/misc/tmpfiles.conf $(DESTDIR)/usr/lib/tmpfiles.d/opencryptoki.conf - $(CHMOD) 0644 $(DESTDIR)/usr/lib/tmpfiles.d/opencryptoki.conf - rm -f $(DESTDIR)/usr/lib/systemd/system/tmpfiles.conf -endif endif $(MKDIR_P) $(DESTDIR)/etc/ld.so.conf.d echo "$(libdir)/opencryptoki" >\ @@ -216,7 +219,7 @@ ci-prepare: killall -HUP pkcsslotd || true - ${srcdir}/testcases/ciconfig.sh "$(sysconfdir)/opencryptoki" "$(sysconfdir)/opencryptoki" + ${srcdir}/testcases/ciconfig.sh "$(sysconfdir)/opencryptoki" "$(sysconfdir)/opencryptoki" "$(sysconfdir)/opencryptoki" @sbindir@/pkcsslotd @sbindir@/pkcsstats --reset-all for slot in `awk '/slot (.*)/ { print $$2; }' $(sysconfdir)/opencryptoki/opencryptoki.conf`; do @sbindir@/pkcsconf -c $$slot -t | grep "Flags:" | grep -q TOKEN_INITIALIZED || PKCS11_USER_PIN=$(PKCS11_USER_PIN) PKCS11_SO_PIN=$(PKCS11_SO_PIN) PKCSLIB=@libdir@/opencryptoki/libopencryptoki.so ${srcdir}/testcases/init_token.sh $$slot; done @@ -239,7 +242,11 @@ ci-installcheck: ci-prepare installcheck killall -HUP pkcsslotd || true @sbindir@/pkcsslotd - cd ${srcdir}/testcases && export PKCSLIB=@libdir@/opencryptoki/libopencryptoki.so && export PKCS11_USER_PIN=$(PKCS11_USER_PIN) && ./misc_tests/p11sak_test.sh | tee log-p11sak.txt + cd ${srcdir}/testcases \ + && export PKCSLIB=@libdir@/opencryptoki/libopencryptoki.so \ + && export PKCS11_USER_PIN=$(PKCS11_USER_PIN) \ + && ./misc_tests/p11sak_test.sh | tee log-p11sak.txt \ + && ./misc_tests/pkcsconf_test.sh | tee log-pkcsconf.txt @sbindir@/pkcsstats --all killall -HUP pkcsslotd @echo "done" diff -Nru opencryptoki-3.18.0+dfsg/man/man1/man1.mk opencryptoki-3.20.0+dfsg/man/man1/man1.mk --- opencryptoki-3.18.0+dfsg/man/man1/man1.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/man/man1/man1.mk 2023-02-13 09:22:42.000000000 +0100 @@ -25,4 +25,4 @@ endif EXTRA_DIST += $(man1_MANS) -CLEANFILES += $(man1_MANS) +CLEANFILES += man/man1/*.1 diff -Nru opencryptoki-3.18.0+dfsg/man/man1/p11sak.1.in opencryptoki-3.20.0+dfsg/man/man1/p11sak.1.in --- opencryptoki-3.18.0+dfsg/man/man1/p11sak.1.in 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/man/man1/p11sak.1.in 2023-02-13 09:22:42.000000000 +0100 @@ -16,7 +16,7 @@ .SH DESCRIPTION .B p11sak can be used to generate, list and delete the token keys in an openCryptoki token repository. -The utility provides a flexible key management tool in openCryptoki to list and generate symmetric (DES; 3DES, AES) and asymetric (RSA, EC) keys. +The utility provides a flexible key management tool in openCryptoki to list and generate symmetric (DES, 3DES, AES, AES-XTS) and asymmetric (RSA, EC, IBM Dilithium, IBM Kyber) keys. This tool is especially capable of a well defined listing of keys with their PKCS #11 attributes. . . @@ -147,6 +147,44 @@ can be used to set the binary attributes of the key (see below for detailed description of the attributes). . .PP +.SS "Generating AES-XTS keys" +. +.B p11sak +.BR generate-key | gen-key | gen +.BR aes-xts +.BR 128 | 256 +.B \-\-slot +.IR SLOTID +.B \-\-pin +.IR PIN +.B \-\-label +.IR LABEL +.B \-\-attr +.IR [P M R L S E D G V W U A X N T] +.B \-\-help | \-h +.PP +Use the +.B generate-key +.B aes-xts +.B 128|256 +command and key argument to generate a AES-XTS key with 128 or 256 bit length, respectively. The +.B \-\-slot +.IR SLOTID +and +.B \-\-pin +.IR PIN +options are required to set the token to +.IR SLOTID +and the token PIN. The +.B \-\-label +option allows the user to set the +.IR LABEL +attribute of the key and +.B \-\-attr +.IR [P M R L S E D G V W U A X N T] +can be used to set the binary attributes of the key (see below for detailed description of the attributes). +. +.PP .SS "Generating RSA keys" . .B p11sak @@ -216,6 +254,7 @@ .B prime256v1 | prime192 | secp224 | secp384r1 | secp521r1 | secp265k1 | brainpoolP160r1 | brainpoolP160t1 .B | brainpoolP192r1 | brainpoolP192t1 | brainpoolP224r1 | brainpoolP224t1 | brainpoolP256r1 | brainpoolP256t1 .B | brainpoolP320r1 | brainpoolP320t1 | brainpoolP384r1 | brainpoolP384t1 | brainpoolP512r1 | brainpoolP512t1 +.B | curve25519 | curve448 | ed25519 | ed448 .PP .B Note: not all curves will be supported by all tokens and key generation will fail when the specified @@ -238,28 +277,116 @@ can be used to set the binary attributes of the key (see below for detailed description of the attributes). . .PP +.SS "Generating IBM Dilithium keys" +. +.B p11sak +.BR generate-key | gen-key | gen +.BR ibm-dilithium +.BR VERSION +.B \-\-slot +.IR SLOTID +.B \-\-pin +.IR PIN +.B \-\-label +.IR LABEL +.B \-\-attr +.IR [M R L S E D G V W U A X N T] +.B \-\-help | \-h +.PP +Use the +.B generate-key +.B ibm-dilithium +.B VERSION +command and key argument to generate an IBM Dilithium key, where +.I VERSION +specifies the version of the IBM Dilithium keypair. The following arguments can be used for respective keys: +.B r2_65 | r2_87 | r3_44 | r3_65 | r3_87 +.PP +The +.B \-\-slot +.IR SLOTID +and +.B \-\-pin +.IR PIN +options are required to set the token to +.IR SLOTID +and the token PIN. The +.B \-\-label +option allows the user to set the +.IR LABEL +attribute of the key and +.B \-\-attr +.IR [M R L S E D G V W U A X N T] +can be used to set the binary attributes of the key (see below for detailed description of the attributes). +. +.PP +.SS "Generating IBM Kyber keys" +. +.B p11sak +.BR generate-key | gen-key | gen +.BR ibm-kyber +.BR VERSION +.B \-\-slot +.IR SLOTID +.B \-\-pin +.IR PIN +.B \-\-label +.IR LABEL +.B \-\-attr +.I [M R L S E D G V W U A X N T] +.B \-\-help | \-h +.PP +Use the +.B generate-key +.B ibm-kyber +.B VERSION +command and key argument to generate an IBM Kyber key, where +.I VERSION +specifies the version of the IBM Kyber keypair. The following arguments can be used for respective keys: +.B r2_768 | r2_1024 +.PP +The +.B \-\-slot +.IR SLOTID +and +.B \-\-pin +.IR PIN +options are required to set the token to +.IR SLOTID +and the token PIN. The +.B \-\-label +option allows the user to set the +.IR LABEL +attribute of the key and +.B \-\-attr +.I [M R L S E D G V W U A X N T] +can be used to set the binary attributes of the key (see below for detailed description of the attributes). +. +.PP .SS "Listing symmetric and asymmetric keys" . .B p11sak .BR list-key | ls-key | ls -.BR des | 3des | aes | rsa | ec | public | private | secret | all +.BR des | 3des | aes | aes-xts | rsa | ec | ibm-dilithium | ibm-kyber | public | private | secret | all .B \-\-slot .IR SLOTID .B \-\-pin .IR PIN +.B \-\-label +.IR LABEL .B \-\-long | \-l .B \-\-help | \-h .PP Use the .B list-key | ls-key | ls -command and key argument to list DES, 3DES, AES, RSA or EC keys, respectively. Public, private, secret, or all keys can also be listed irrespective of key type. +command and key argument to list DES, 3DES, AES, AES-XTS, RSA, EC, IBM Dilithium, or IBM Kyber keys, respectively. Public, private, secret, or all keys can also be listed irrespective of key type. . .PP .SS "Deleting symmetric and asymmetric keys" . .B p11sak .BR remove-key | rm-key | rm -.BR des | 3des | aes | rsa | ec +.BR des | 3des | aes | aes-xts | rsa | ec | ibm-dilithium | ibm-kyber .B \-\-slot .IR SLOTID .B \-\-pin @@ -271,7 +398,7 @@ .PP Use the .B remove-key | rm-key | rm -command and key argument to delete DES, 3DES, AES, RSA, or EC keys, respectively. All specified cipher keys will be promted to be deleted unless +command and key argument to delete DES, 3DES, AES, AES-XTS, RSA, EC, IBM Dilithium, or IBM Kyber keys, respectively. All specified cipher keys will be prompted to be deleted unless a specific key with the .B \-\-label .IR LABEL @@ -285,9 +412,9 @@ . .SH ARGS . -.SS "des | 3des | aes | rsa | ec | public | private | secret | all" +.SS "des | 3des | aes | aes-xts | rsa | ec | ibm-dilithium | ibm-kyber | public | private | secret | all" -selects the respective symmetric or asymetric key to be generated or listed. The +selects the respective symmetric or asymmetric key to be generated or listed. The .B public|private|secret|all argument can only be used with the .B list-key @@ -304,6 +431,14 @@ . . . +.SS "128|256" +the +.B aes-xts +argument has to be followed by either 128 or 256 to set the respective key bit length of the AES-XTS key. +.PP +. +. +. .SS "1024|2048|4096" the .B rsa @@ -312,7 +447,7 @@ . . . -.SS "prime256v1 | prime192 | secp224 | secp384r1 | secp521r1 | secp265k1 | brainpoolP160r1 | brainpoolP160t1 | brainpoolP192r1 | brainpoolP192t1 | brainpoolP224r1 | brainpoolP224t1 | brainpoolP256r1 | brainpoolP256t1 | brainpoolP320r1 | brainpoolP320t1 | brainpoolP384r1 | brainpoolP384t1 | brainpoolP512r1 | brainpoolP512t1" +.SS "prime256v1 | prime192 | secp224 | secp384r1 | secp521r1 | secp265k1 | brainpoolP160r1 | brainpoolP160t1 | brainpoolP192r1 | brainpoolP192t1 | brainpoolP224r1 | brainpoolP224t1 | brainpoolP256r1 | brainpoolP256t1 | brainpoolP320r1 | brainpoolP320t1 | brainpoolP384r1 | brainpoolP384t1 | brainpoolP512r1 | brainpoolP512t1 | curve25519 | curve448 | ed25519 | ed448" the .B ec argument has to be followed by either of these @@ -322,6 +457,26 @@ . . +.SS "r2_6|r2_87|r3_44|r3_65|r3_875" +the +.B ibm-dilithium +argument has to be followed by either of these +.I VERSION +to select the IBM dilithium version used to generate the key. +.PP +. +. +. +.SS "r2_768|r2_1024" +the +.B ibm-kyber +argument has to be followed by either of these +.I VERSION +to select the IBM kyber version used to generate the key. +.PP +. +. +. .SH OPTIONS .SS "\-\-slot SLOTID" @@ -335,6 +490,16 @@ sets the token PIN to .IR PIN .PP +Alternatively the PKCS11_USER_PIN environment variable may be used to +provide the token PIN. +.PP +. +. +. +.SS "\-\-force-pin-prompt" +enforce p11sak to prompt for the token PIN (regardless if it has been +specified elsewhere) +.PP . . . @@ -342,6 +507,22 @@ sets the key label attribute to .IR LABEL .PP +For asymmetric keys, the specified label is appended by \fB:pub\fP and +\fB.prv\fP for the public and private key objects. Optionally, a user can set +different labels for the public and private key objects by specifying them +separated by a colon (\fB:\fP), e.g. \fBpub-label:priv-label\fP. The label +string in front of the colon is used as label for the public key object, the +label string after the colon is used for the private key object. +To set the public and private key label the exact same, use \fBpub-label:=\fP. +The equal sign (\fB=\fP) means to use the same label string for the private +key objects as for the public key object. +In case a colon character or a equal sign is supposed to appear within +a label string, it must be escaped using a back slash (\fB\\\fP), e.g. +\fBabc\\:xyz\fP results in \fBabx:xyz\fP where the colon is not treated as +separator character. +Note that the shell may interpret escape characters as well, so better quote +the \fILABEL\fP specification. +.PP . . . @@ -467,6 +648,12 @@ P11SAK_DEFAULT_CONF_FILE. If none is set p11sak will first look for the file in the user directory, followed by the standard installation path. .PP +.SS "PKCS11_USER_PIN" +The token PIN can be specified via the environment variable PKCS11_USER_PIN. +If nothing is set and the option +.B \-\-pin +is not specified, p11sak will prompt for the token PIN interactively. +.PP . . . diff -Nru opencryptoki-3.18.0+dfsg/man/man1/pkcscca.1.in opencryptoki-3.20.0+dfsg/man/man1/pkcscca.1.in --- opencryptoki-3.18.0+dfsg/man/man1/pkcscca.1.in 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/man/man1/pkcscca.1.in 2023-02-13 09:22:42.000000000 +0100 @@ -15,6 +15,12 @@ [\fB-k aes|apka|asym|sym\fP] [\fIOPTIONS\fP] +.SS "OLD RSA KEY MIGRATION" +\fBpkcscca\fP +[\fB-m oldrsakeys\fP] +[\fB-s SLOTID\fP] +[\fIOPTIONS\fP] + .SH DESCRIPTION The \fBpkcscca\fP utility assists in administering the CCA token. @@ -32,6 +38,17 @@ by unwrapping them with the old master key and wrapping them with the current master key. +Up to opencryptoki version 3.14.0, RSA keys were created using the RSA-CRT +key token format (private key section X'08'). RSA-CRT keys are encrypted with +the CCA ASYM master key, and can not be used for certain mechanisms, e.g. +RSA-PSS or RSA-OAEP. In newer opencryptoki versions, RSA keys are created using +the RSA-AESC key token format (private key section X'31'). Up to version 3.16.0, +RSA public keys also contained full CCA secure key tokens, including the private +key section (which is encrypted by the CCA master key). The \fBoldrsakeys\fP +migration option migrates old RSA private key tokens to the new format, and also +extracts the public key sections from RSA public key tokens containing a full +CCA secure key token. + .SH "GENERAL OPTIONS" .IP "\fB-d|--datastore\fP \fIdirectory\fp" 10 the directory where the CCA token information is kept. This directory will be @@ -53,6 +70,13 @@ .IP "\fB-s|--slotid\fP \fISLOTID\fP" 5 The PKCS slot number. +.SH "OLD RSA KEY MIGRATION" +.IP "\fB-m oldrsakeys\fP" 5 +Converts old RSA keys (RSA-CRT) to the new format (RSA-AESC) and extracts the +public key section only from key objects containing the full RSA key token. +.IP "\fB-s|--slotid\fP \fISLOTID\fP" 5 +The PKCS slot number. + .SH "FILES" .IP "/var/lib/opencryptoki/ccatok/TOK_OBJ/OBJ.IDX" contains current list of public and private token objects for the CCA token. diff -Nru opencryptoki-3.18.0+dfsg/man/man5/man5.mk opencryptoki-3.20.0+dfsg/man/man5/man5.mk --- opencryptoki-3.18.0+dfsg/man/man5/man5.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/man/man5/man5.mk 2023-02-13 09:22:42.000000000 +0100 @@ -5,4 +5,4 @@ endif EXTRA_DIST += $(man5_MANS) -CLEANFILES += $(man5_MANS) +CLEANFILES += man/man5/*.5 diff -Nru opencryptoki-3.18.0+dfsg/man/man5/policy.conf.5.in opencryptoki-3.20.0+dfsg/man/man5/policy.conf.5.in --- opencryptoki-3.18.0+dfsg/man/man5/policy.conf.5.in 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/man/man5/policy.conf.5.in 2023-02-13 09:22:42.000000000 +0100 @@ -133,7 +133,7 @@ .BR allowedkdfs This key specifies the allowed Key Derivation Functions (KDFs) for use -in ECDH key derivation. The value is a list of +in ECDH key derivation and Kyber KEM. The value is a list of .BR CKD_ constants supported by openCryptoki. This list has the same format as the diff -Nru opencryptoki-3.18.0+dfsg/man/man7/man7.mk opencryptoki-3.20.0+dfsg/man/man7/man7.mk --- opencryptoki-3.18.0+dfsg/man/man7/man7.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/man/man7/man7.mk 2023-02-13 09:22:42.000000000 +0100 @@ -1,4 +1,4 @@ man7_MANS += man/man7/opencryptoki.7 EXTRA_DIST += $(man7_MANS) -CLEANFILES += $(man7_MANS) +CLEANFILES += man/man7/*.7 diff -Nru opencryptoki-3.18.0+dfsg/man/man8/man8.mk opencryptoki-3.20.0+dfsg/man/man8/man8.mk --- opencryptoki-3.18.0+dfsg/man/man8/man8.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/man/man8/man8.mk 2023-02-13 09:22:42.000000000 +0100 @@ -1,4 +1,4 @@ man8_MANS += man/man8/pkcsslotd.8 EXTRA_DIST += $(man8_MANS) -CLEANFILES += $(man8_MANS) +CLEANFILES += man/man8/*.8 diff -Nru opencryptoki-3.18.0+dfsg/misc/mech_list.c opencryptoki-3.20.0+dfsg/misc/mech_list.c --- opencryptoki-3.18.0+dfsg/misc/mech_list.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/misc/mech_list.c 1970-01-01 01:00:00.000000000 +0100 @@ -1,161 +0,0 @@ -/* - * COPYRIGHT (c) International Business Machines Corp. 2005-2017 - * - * This program is provided under the terms of the Common Public License, - * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this - * software constitutes recipient's acceptance of CPL-1.0 terms which can be - * found in the file LICENSE file or at - * https://opensource.org/licenses/cpl1.0.php - */ - -/** - * This is an example of how you might convert your library's internal - * mechanism descriptors into PKCS#11-compatible descriptors while - * generating a mechanism list for openCryptoki. - */ - -#include "mech_types.h" - -#ifndef NULL -#define NULL 0 -#endif - -/** - * Bogus internal data descriptors for various mechanisms. - */ -#define CUSTOM_MECH_TDES 1 -#define CUSTOM_MECH_BLOWFISH 2 -#define CUSTOM_MECH_RIPEMD160 3 -#define CUSTOM_MECH_DSA 4 - -/** - * An example of a library's way of representing a mechanism. - */ -struct custom_mech_descriptor { - int mech_type; - int min_key_size; - int max_key_size; - int is_hw_accelerated; - int support_encrypt; - int support_decrypt; - int support_digest; - int support_wrap; - int support_unwrap; - int support_sign; - int support_verify; -}; - -/** - * Something like this should actually be filled in by querying the - * driver for what is available; if the library supports software - * fallback, then the CKF_HW flag should not be set so openCryptoki is - * aware of what really is hardware accelerated and what is not. - */ -struct custom_mech_descriptor library_specific_mechs[] = { - {CUSTOM_MECH_TDES, 24, 24, 1, 1, 1, 0, 1, 1, 0, 0}, - {CUSTOM_MECH_BLOWFISH, 16, 16, 1, 1, 1, 0, 1, 1, 0, 0}, - {CUSTOM_MECH_RIPEMD160, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0}, - {CUSTOM_MECH_DSA, 512, 4096, 1, 0, 0, 0, 0, 0, 1, 1} -}; -#define CUSTOM_MECH_ARRAY_SIZE 4 - -/** - * Here is an example of how you might map your driver's type - * descriptors to the PKCS#11 type descriptors - */ -struct mech_type_mapping { - int internal_mech_type; - CK_MECHANISM_TYPE pkcs11_mech_type; -}; - -/** - * The mapping from the internal driver type to the PKCS#11 type. - */ -struct mech_type_mapping mech_type_map[] = { - {CUSTOM_MECH_TDES, CKM_DES3_CBC}, - {CUSTOM_MECH_BLOWFISH, CKM_VENDOR_DEFINED}, - {CUSTOM_MECH_RIPEMD160, CKM_RIPEMD160}, - {CUSTOM_MECH_DSA, CKM_DSA} -}; -#define MECH_TYPE_MAP_SIZE 4 - -static CK_MECHANISM_TYPE pkcs11_mech_type_for_internal_type(int internal_type) -{ - int i = 0; - CK_MECHANISM_TYPE pkcs11_type = CKM_VENDOR_DEFINED; - while (i < MECH_TYPE_MAP_SIZE) { - if (mech_type_map[i].internal_mech_type == internal_type) { - pkcs11_type = mech_type_map[i].pkcs11_mech_type; - break; - } - i++; - } - return pkcs11_type; -} - -/** - * Example method that converts a library's internal mechanism - * descriptor into a PKCS#11 mechanism descriptor. Yours may look very - * different from this one... - */ -static void convert_internal_element_to_pkcs11_method_element( - MECH_LIST_ELEMENT *element, - struct custom_mech_descriptor *internal_mech) -{ - element->mech_type = - pkcs11_mech_type_for_internal_type(internal_mech->mech_type); - element->mech_info.ulMinKeySize = internal_mech->min_key_size; - element->mech_info.ulMaxKeySize = internal_mech->max_key_size; - element->mech_info.flags = 0; - /* Partial example list of flags that could be set */ - if (internal_mech->is_hw_accelerated) { - element->mech_info.flags |= CKF_HW; - } - if (internal_mech->support_encrypt) { - element->mech_info.flags |= CKF_ENCRYPT; - } - if (internal_mech->support_decrypt) { - element->mech_info.flags |= CKF_DECRYPT; - } - if (internal_mech->support_digest) { - element->mech_info.flags |= CKF_DIGEST; - } - if (internal_mech->support_wrap) { - element->mech_info.flags |= CKF_WRAP; - } - if (internal_mech->support_unwrap) { - element->mech_info.flags |= CKF_UNWRAP; - } - if (internal_mech->support_sign) { - element->mech_info.flags |= CKF_SIGN; - } - if (internal_mech->support_verify) { - element->mech_info.flags |= CKF_VERIFY; - } - /* ... */ -} - -/** - * Generates a list of supported mechanisms. This is the function that - * openCryptoki will be calling directly with a pointer to a - * placeholder mech_list struct. - * - * @param head Pointer to placeholder mech_list struct; this function - * fills in the list by tagging on newly malloc'd - * mech_list structs off of this struct. - */ -void generate_pkcs11_mech_list(struct mech_list *head) -{ - struct mech_list *item; - int i = 0; - item = head; - while (i < CUSTOM_MECH_ARRAY_SIZE) { - item->next = malloc(sizeof(struct mech_list)); - item = item->next; - convert_internal_element_to_pkcs11_method_element( - &item->element, &library_specific_mechs[i]); - i++; - } - item->next = NULL; - return; -} diff -Nru opencryptoki-3.18.0+dfsg/misc/mech_types.h opencryptoki-3.20.0+dfsg/misc/mech_types.h --- opencryptoki-3.18.0+dfsg/misc/mech_types.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/misc/mech_types.h 1970-01-01 01:00:00.000000000 +0100 @@ -1,344 +0,0 @@ -/* - * COPYRIGHT (c) International Business Machines Corp. 2005-2017 - * - * This program is provided under the terms of the Common Public License, - * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this - * software constitutes recipient's acceptance of CPL-1.0 terms which can be - * found in the file LICENSE file or at - * https://opensource.org/licenses/cpl1.0.php - */ - -#ifndef _MECH_LIST_TYPES_H -#define _MECH_LIST_TYPES_H - - -/** - * These defines are copied over from the pkcs11types.h file found in - * the openCryptoki package. - */ -/* An unsigned value, at least 32 bits long */ -typedef unsigned long int CK_ULONG; - -/* A signed value, the same size as a CK_ULONG */ -/* CK_LONG is new for v2.0 */ -typedef long int CK_LONG; - -/* At least 32 bits; each bit is a Boolean flag */ -typedef CK_ULONG CK_FLAGS; - -/* CK_MECHANISM_TYPE is a value that identifies a mechanism - * type */ -typedef CK_ULONG CK_MECHANISM_TYPE; - -/* The following mechanism types are defined: */ -#define CKM_RSA_PKCS_KEY_PAIR_GEN 0x00000000 -#define CKM_RSA_PKCS 0x00000001 -#define CKM_RSA_9796 0x00000002 -#define CKM_RSA_X_509 0x00000003 - -/* CKM_MD2_RSA_PKCS, CKM_MD5_RSA_PKCS, and CKM_SHA1_RSA_PKCS - * are new for v2.0. They are mechanisms which hash and sign */ -#define CKM_MD2_RSA_PKCS 0x00000004 -#define CKM_MD5_RSA_PKCS 0x00000005 -#define CKM_SHA1_RSA_PKCS 0x00000006 -/* The following are new for v2.11: */ -#define CKM_RIPEMD128_RSA_PKCS 0x00000007 -#define CKM_RIPEMD160_RSA_PKCS 0x00000008 -#define CKM_RSA_PKCS_OAEP 0x00000009 -#define CKM_RSA_X9_31_KEY_PAIR_GEN 0x0000000A -#define CKM_RSA_X9_31 0x0000000B -#define CKM_SHA1_RSA_X9_31 0x0000000C -#define CKM_RSA_PKCS_PSS 0x0000000D -#define CKM_SHA1_RSA_PKCS_PSS 0x0000000E - -#define CKM_DSA_KEY_PAIR_GEN 0x00000010 -#define CKM_DSA 0x00000011 -#define CKM_DSA_SHA1 0x00000012 -#define CKM_DH_PKCS_KEY_PAIR_GEN 0x00000020 -#define CKM_DH_PKCS_DERIVE 0x00000021 -/* The following are new for v2.11 */ -#define CKM_X9_42_DH_KEY_PAIR_GEN 0x00000030 -#define CKM_X9_42_DH_DERIVE 0x00000031 -#define CKM_X9_42_DH_HYBRID_DERIVE 0x00000032 -#define CKM_X9_42_MQV_DERIVE 0x00000033 - -#define CKM_RC2_KEY_GEN 0x00000100 -#define CKM_RC2_ECB 0x00000101 -#define CKM_RC2_CBC 0x00000102 -#define CKM_RC2_MAC 0x00000103 - -/* CKM_RC2_MAC_GENERAL and CKM_RC2_CBC_PAD are new for v2.0 */ -#define CKM_RC2_MAC_GENERAL 0x00000104 -#define CKM_RC2_CBC_PAD 0x00000105 - -#define CKM_RC4_KEY_GEN 0x00000110 -#define CKM_RC4 0x00000111 -#define CKM_DES_KEY_GEN 0x00000120 -#define CKM_DES_ECB 0x00000121 -#define CKM_DES_CBC 0x00000122 -#define CKM_DES_MAC 0x00000123 - -/* CKM_DES_MAC_GENERAL and CKM_DES_CBC_PAD are new for v2.0 */ -#define CKM_DES_MAC_GENERAL 0x00000124 -#define CKM_DES_CBC_PAD 0x00000125 - -#define CKM_DES2_KEY_GEN 0x00000130 -#define CKM_DES3_KEY_GEN 0x00000131 -#define CKM_DES3_ECB 0x00000132 -#define CKM_DES3_CBC 0x00000133 -#define CKM_DES3_MAC 0x00000134 - -/* CKM_DES3_MAC_GENERAL, CKM_DES3_CBC_PAD, CKM_CDMF_KEY_GEN, - * CKM_CDMF_ECB, CKM_CDMF_CBC, CKM_CDMF_MAC, - * CKM_CDMF_MAC_GENERAL, and CKM_CDMF_CBC_PAD are new for v2.0 */ -#define CKM_DES3_MAC_GENERAL 0x00000135 -#define CKM_DES3_CBC_PAD 0x00000136 -#define CKM_DES3_CMAC_GENERAL 0x00000137 -#define CKM_DES3_CMAC 0x00000138 -#define CKM_CDMF_KEY_GEN 0x00000140 -#define CKM_CDMF_ECB 0x00000141 -#define CKM_CDMF_CBC 0x00000142 -#define CKM_CDMF_MAC 0x00000143 -#define CKM_CDMF_MAC_GENERAL 0x00000144 -#define CKM_CDMF_CBC_PAD 0x00000145 - -#define CKM_MD2 0x00000200 - -/* CKM_MD2_HMAC and CKM_MD2_HMAC_GENERAL are new for v2.0 */ -#define CKM_MD2_HMAC 0x00000201 -#define CKM_MD2_HMAC_GENERAL 0x00000202 - -#define CKM_MD5 0x00000210 - -/* CKM_MD5_HMAC and CKM_MD5_HMAC_GENERAL are new for v2.0 */ -#define CKM_MD5_HMAC 0x00000211 -#define CKM_MD5_HMAC_GENERAL 0x00000212 - -#define CKM_SHA_1 0x00000220 - -/* CKM_SHA_1_HMAC and CKM_SHA_1_HMAC_GENERAL are new for v2.0 */ -#define CKM_SHA_1_HMAC 0x00000221 -#define CKM_SHA_1_HMAC_GENERAL 0x00000222 - -/* The following are new for v2.11 */ -#define CKM_RIPEMD128 0x00000230 -#define CKM_RIPEMD128_HMAC 0x00000231 -#define CKM_RIPEMD128_HMAC_GENERAL 0x00000232 -#define CKM_RIPEMD160 0x00000240 -#define CKM_RIPEMD160_HMAC 0x00000241 -#define CKM_RIPEMD160_HMAC_GENERAL 0x00000242 - -/* All of the following mechanisms are new for v2.0 */ -/* Note that CAST128 and CAST5 are the same algorithm */ -#define CKM_CAST_KEY_GEN 0x00000300 -#define CKM_CAST_ECB 0x00000301 -#define CKM_CAST_CBC 0x00000302 -#define CKM_CAST_MAC 0x00000303 -#define CKM_CAST_MAC_GENERAL 0x00000304 -#define CKM_CAST_CBC_PAD 0x00000305 -#define CKM_CAST3_KEY_GEN 0x00000310 -#define CKM_CAST3_ECB 0x00000311 -#define CKM_CAST3_CBC 0x00000312 -#define CKM_CAST3_MAC 0x00000313 -#define CKM_CAST3_MAC_GENERAL 0x00000314 -#define CKM_CAST3_CBC_PAD 0x00000315 -#define CKM_CAST5_KEY_GEN 0x00000320 -#define CKM_CAST128_KEY_GEN 0x00000320 -#define CKM_CAST5_ECB 0x00000321 -#define CKM_CAST128_ECB 0x00000321 -#define CKM_CAST5_CBC 0x00000322 -#define CKM_CAST128_CBC 0x00000322 -#define CKM_CAST5_MAC 0x00000323 -#define CKM_CAST128_MAC 0x00000323 -#define CKM_CAST5_MAC_GENERAL 0x00000324 -#define CKM_CAST128_MAC_GENERAL 0x00000324 -#define CKM_CAST5_CBC_PAD 0x00000325 -#define CKM_CAST128_CBC_PAD 0x00000325 -#define CKM_RC5_KEY_GEN 0x00000330 -#define CKM_RC5_ECB 0x00000331 -#define CKM_RC5_CBC 0x00000332 -#define CKM_RC5_MAC 0x00000333 -#define CKM_RC5_MAC_GENERAL 0x00000334 -#define CKM_RC5_CBC_PAD 0x00000335 -#define CKM_IDEA_KEY_GEN 0x00000340 -#define CKM_IDEA_ECB 0x00000341 -#define CKM_IDEA_CBC 0x00000342 -#define CKM_IDEA_MAC 0x00000343 -#define CKM_IDEA_MAC_GENERAL 0x00000344 -#define CKM_IDEA_CBC_PAD 0x00000345 -#define CKM_GENERIC_SECRET_KEY_GEN 0x00000350 -#define CKM_CONCATENATE_BASE_AND_KEY 0x00000360 -#define CKM_CONCATENATE_BASE_AND_DATA 0x00000362 -#define CKM_CONCATENATE_DATA_AND_BASE 0x00000363 -#define CKM_XOR_BASE_AND_DATA 0x00000364 -#define CKM_EXTRACT_KEY_FROM_KEY 0x00000365 -#define CKM_SSL3_PRE_MASTER_KEY_GEN 0x00000370 -#define CKM_SSL3_MASTER_KEY_DERIVE 0x00000371 -#define CKM_SSL3_KEY_AND_MAC_DERIVE 0x00000372 -/* The following are new for v2.11 */ -#define CKM_SSL3_MASTER_KEY_DERIVE_DH 0x00000373 -#define CKM_TLS_PRE_MASTER_KEY_GEN 0x00000374 -#define CKM_TLS_MASTER_KEY_DERIVE 0x00000375 -#define CKM_TLS_KEY_AND_MAC_DERIVE 0x00000376 -#define CKM_TLS_MASTER_KEY_DERIVE_DH 0x00000377 - -#define CKM_SSL3_MD5_MAC 0x00000380 -#define CKM_SSL3_SHA1_MAC 0x00000381 -#define CKM_MD5_KEY_DERIVATION 0x00000390 -#define CKM_MD2_KEY_DERIVATION 0x00000391 -#define CKM_SHA1_KEY_DERIVATION 0x00000392 -#define CKM_PBE_MD2_DES_CBC 0x000003A0 -#define CKM_PBE_MD5_DES_CBC 0x000003A1 -#define CKM_PBE_MD5_CAST_CBC 0x000003A2 -#define CKM_PBE_MD5_CAST3_CBC 0x000003A3 -#define CKM_PBE_MD5_CAST5_CBC 0x000003A4 -#define CKM_PBE_MD5_CAST128_CBC 0x000003A4 -#define CKM_PBE_SHA1_CAST5_CBC 0x000003A5 -#define CKM_PBE_SHA1_CAST128_CBC 0x000003A5 -#define CKM_PBE_SHA1_RC4_128 0x000003A6 -#define CKM_PBE_SHA1_RC4_40 0x000003A7 -#define CKM_PBE_SHA1_DES3_EDE_CBC 0x000003A8 -#define CKM_PBE_SHA1_DES2_EDE_CBC 0x000003A9 -#define CKM_PBE_SHA1_RC2_128_CBC 0x000003AA -#define CKM_PBE_SHA1_RC2_40_CBC 0x000003AB -/* CKM_PKCS5_PBKD2 is new for v2.11 */ -#define CKM_PKCS5_PBKD2 0x000003B0 -#define CKM_PBA_SHA1_WITH_SHA1_HMAC 0x000003C0 -#define CKM_KEY_WRAP_LYNKS 0x00000400 -#define CKM_KEY_WRAP_SET_OAEP 0x00000401 - -/* Fortezza mechanisms */ -#define CKM_SKIPJACK_KEY_GEN 0x00001000 -#define CKM_SKIPJACK_ECB64 0x00001001 -#define CKM_SKIPJACK_CBC64 0x00001002 -#define CKM_SKIPJACK_OFB64 0x00001003 -#define CKM_SKIPJACK_CFB64 0x00001004 -#define CKM_SKIPJACK_CFB32 0x00001005 -#define CKM_SKIPJACK_CFB16 0x00001006 -#define CKM_SKIPJACK_CFB8 0x00001007 -#define CKM_SKIPJACK_WRAP 0x00001008 -#define CKM_SKIPJACK_PRIVATE_WRAP 0x00001009 -#define CKM_SKIPJACK_RELAYX 0x0000100a -#define CKM_KEA_KEY_PAIR_GEN 0x00001010 -#define CKM_KEA_KEY_DERIVE 0x00001011 -#define CKM_FORTEZZA_TIMESTAMP 0x00001020 -#define CKM_BATON_KEY_GEN 0x00001030 -#define CKM_BATON_ECB128 0x00001031 -#define CKM_BATON_ECB96 0x00001032 -#define CKM_BATON_CBC128 0x00001033 -#define CKM_BATON_COUNTER 0x00001034 -#define CKM_BATON_SHUFFLE 0x00001035 -#define CKM_BATON_WRAP 0x00001036 - -/* CKM_ECDSA_KEY_PAIR_GEN is deprecated in v2.11, - * CKM_EC_KEY_PAIR_GEN is preferred. */ -#define CKM_ECDSA_KEY_PAIR_GEN 0x00001040 -#define CKM_EC_KEY_PAIR_GEN 0x00001040 -#define CKM_ECDSA 0x00001041 -#define CKM_ECDSA_SHA1 0x00001042 -/* The following are new for v2.3 */ -#define CKM_ECDSA_SHA224 0x00001043 -#define CKM_ECDSA_SHA256 0x00001044 -#define CKM_ECDSA_SHA384 0x00001045 -#define CKM_ECDSA_SHA512 0x00001046 -/* The following are new for v2.11 */ -#define CKM_ECDH1_DERIVE 0x00001050 -#define CKM_ECDH1_COFACTOR_DERIVE 0x00001051 -#define CKM_ECMQV_DERIVE 0x00001052 - -#define CKM_JUNIPER_KEY_GEN 0x00001060 -#define CKM_JUNIPER_ECB128 0x00001061 -#define CKM_JUNIPER_CBC128 0x00001062 -#define CKM_JUNIPER_COUNTER 0x00001063 -#define CKM_JUNIPER_SHUFFLE 0x00001064 -#define CKM_JUNIPER_WRAP 0x00001065 -#define CKM_FASTHASH 0x00001070 -/* The following are new for v2.11 */ -#define CKM_AES_KEY_GEN 0x00001080 -#define CKM_AES_ECB 0x00001081 -#define CKM_AES_CBC 0x00001082 -#define CKM_AES_MAC 0x00001083 -#define CKM_AES_MAC_GENERAL 0x00001084 -#define CKM_AES_CBC_PAD 0x00001085 -#define CKM_AES_CMAC_GENERAL 0x00001089 -#define CKM_AES_CMAC 0x0000108A -#define CKM_DSA_PARAMETER_GEN 0x00002000 -#define CKM_DH_PKCS_PARAMETER_GEN 0x00002001 -#define CKM_X9_42_DH_PARAMETER_GEN 0x00002002 - -#define CKM_VENDOR_DEFINED 0x80000000 - -#define CK_PTR * -typedef void CK_PTR CK_VOID_PTR; -typedef CK_VOID_PTR CK_PTR CK_VOID_PTR_PTR; - -/* CK_MECHANISM is a structure that specifies a particular - * mechanism */ -typedef struct CK_MECHANISM { - CK_MECHANISM_TYPE mechanism; - CK_VOID_PTR pParameter; - CK_ULONG ulParameterLen; /* in bytes */ -} CK_MECHANISM; - -typedef CK_MECHANISM CK_PTR CK_MECHANISM_PTR; - -/* CK_MECHANISM_INFO provides information about a particular - * mechanism */ -typedef struct CK_MECHANISM_INFO { - CK_ULONG ulMinKeySize; - CK_ULONG ulMaxKeySize; - CK_FLAGS flags; -} CK_MECHANISM_INFO; - -/* The flags are defined as follows: - * Bit Flag Mask Meaning */ -#define CKF_HW 0x00000001 /* performed by HW */ - -/* The flags CKF_ENCRYPT, CKF_DECRYPT, CKF_DIGEST, CKF_SIGN, - * CKG_SIGN_RECOVER, CKF_VERIFY, CKF_VERIFY_RECOVER, - * CKF_GENERATE, CKF_GENERATE_KEY_PAIR, CKF_WRAP, CKF_UNWRAP, - * and CKF_DERIVE are new for v2.0. They specify whether or not - * a mechanism can be used for a particular task */ -#define CKF_ENCRYPT 0x00000100 -#define CKF_DECRYPT 0x00000200 -#define CKF_DIGEST 0x00000400 -#define CKF_SIGN 0x00000800 -#define CKF_SIGN_RECOVER 0x00001000 -#define CKF_VERIFY 0x00002000 -#define CKF_VERIFY_RECOVER 0x00004000 -#define CKF_GENERATE 0x00008000 -#define CKF_GENERATE_KEY_PAIR 0x00010000 -#define CKF_WRAP 0x00020000 -#define CKF_UNWRAP 0x00040000 -#define CKF_DERIVE 0x00080000 -/* The following are new for v2.11 */ -#define CKF_EC_F_P 0x00100000 -#define CKF_EC_F_2M 0x00200000 -#define CKF_EC_ECPARAMETERS 0x00400000 -#define CKF_EC_NAMEDCURVE 0x00800000 -#define CKF_EC_UNCOMPRESS 0x01000000 -#define CKF_EC_COMPRESS 0x02000000 - -#define CKF_EXTENSION 0x80000000 /* FALSE for 2.01 */ - -typedef CK_MECHANISM_INFO CK_PTR CK_MECHANISM_INFO_PTR; - -#define CKR_MECHANISM_INVALID 0x00000070 -#define CKR_MECHANISM_PARAM_INVALID 0x00000071 - - -/* From common/host_defs.h in openCryptoki */ -typedef struct _MECH_LIST_ELEMENT -{ - CK_MECHANISM_TYPE mech_type; - CK_MECHANISM_INFO mech_info; -} MECH_LIST_ELEMENT; - -struct mech_list; - -struct mech_list { - struct mech_list *next; - MECH_LIST_ELEMENT element; -}; - -#endif diff -Nru opencryptoki-3.18.0+dfsg/misc/migrate_from_2.1_to_2.2.sh opencryptoki-3.20.0+dfsg/misc/migrate_from_2.1_to_2.2.sh --- opencryptoki-3.18.0+dfsg/misc/migrate_from_2.1_to_2.2.sh 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/misc/migrate_from_2.1_to_2.2.sh 1970-01-01 01:00:00.000000000 +0100 @@ -1,34 +0,0 @@ -#!/bin/sh -# -# COPYRIGHT (c) International Business Machines Corp. 2006-2017 -# -# This program is provided under the terms of the Common Public License, -# version 1.0 (CPL-1.0). Any use, reproduction or distribution for this software -# constitutes recipient's acceptance of CPL-1.0 terms which can be found -# in the file LICENSE file or at https://opensource.org/licenses/cpl1.0.php -# - -# This script should be run after installing openCryptoki version 2.2.x on a -# machine where openCryptoki version 2.1.x has already been installed. - -# Make sure that no copies of pkcsslotd are running -ps -ef | grep pkcsslotd | grep sbin &> /dev/null -RES=$? -if [ $RES = 0 ]; then - killall pkcsslotd -fi - -# Copy files from /etc/pkcs11/ to /var/lib/opencryptoki/ -if [ -e "/etc/pkcs11" ]; then - mkdir -p /var/lib/opencryptoki - cp -aR /etc/pkcs11/* /var/lib/opencryptoki/ - cp -a /etc/pkcs11/.slotpid /var/lib/opencryptoki/ -fi - -# Run startup script -/usr/sbin/pkcs11_startup - -# Restart pkcsslotd if it was running before this script was run -if [ $RES = 0 ]; then - /usr/sbin/pkcsslotd -fi diff -Nru opencryptoki-3.18.0+dfsg/misc/misc.mk opencryptoki-3.20.0+dfsg/misc/misc.mk --- opencryptoki-3.18.0+dfsg/misc/misc.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/misc/misc.mk 2023-02-13 09:22:42.000000000 +0100 @@ -20,21 +20,27 @@ TOKENS += icsf endif -EXTRA_DIST += \ - misc/pkcsslotd.in misc/pkcsslotd.service.in misc/tmpfiles.conf.in +EXTRA_DIST += misc/pkcsslotd.in misc/pkcsslotd.service.in \ + misc/tmpfiles.conf.in misc/opencryptoki.pc.in + +pkgconfigdir = $(libdir)/pkgconfig +pkgconfig_DATA = misc/opencryptoki.pc if ENABLE_DAEMON if ENABLE_SYSTEMD servicedir = $(unitdir) -service_DATA = misc/pkcsslotd.service misc/tmpfiles.conf +service_DATA = misc/pkcsslotd.service -CLEANFILES += misc/pkcsslotd.service misc/tmpfiles.conf +tmpfilesdir = /usr/lib/tmpfiles.d +tmpfiles_DATA = misc/opencryptoki.conf + +CLEANFILES += misc/pkcsslotd.service misc/opencryptoki.conf ${srcdir}/misc/pkcsslotd.service: ${srcdir}/misc/pkcsslotd.service.in @SED@ -e s!\@sbindir\@!"@sbindir@"!g < $< > $@-t mv $@-t $@ -${srcdir}/misc/tmpfiles.conf: ${srcdir}/misc/tmpfiles.conf.in +${srcdir}/misc/opencryptoki.conf: ${srcdir}/misc/tmpfiles.conf.in @SED@ -e s!\@lockdir\@!$(lockdir)!g < $< > $@-t $(foreach TOK,$(TOKENS),\ echo "D $(lockdir)/$(TOK) 0770 root pkcs11 -" >> $@-t;) diff -Nru opencryptoki-3.18.0+dfsg/misc/opencryptoki.gdb opencryptoki-3.20.0+dfsg/misc/opencryptoki.gdb --- opencryptoki-3.18.0+dfsg/misc/opencryptoki.gdb 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/misc/opencryptoki.gdb 1970-01-01 01:00:00.000000000 +0100 @@ -1,185 +0,0 @@ -# -# COPYRIGHT (c) International Business Machines Corp. 2011-2017 -# -# This program is provided under the terms of the Common Public License, -# version 1.0 (CPL-1.0). Any use, reproduction or distribution for this software -# constitutes recipient's acceptance of CPL-1.0 terms which can be found -# in the file LICENSE file or at https://opensource.org/licenses/cpl1.0.php -# -# openCryptoki debugging helper script -# -# Kent Yoder -# April 29, 2011 -# -# Functions: -# -# ock_dump_obj_template -# ock_dump_object_map -# ock_dump_sess_btree -# ock_dump_sess_obj_btree -# ock_dump_priv_tok_obj_btree -# ock_dump_publ_tok_obj_btree -# - -set $OBJECT_MAP = 1 -set $OBJECT = 2 -set $SESSION = 3 - -# -# ock_dump_obj_template -# -# Dump an OBJECT's template of attributes -# -define ock_dump_obj_template - set $obj = ($arg0) - set $node = $obj->template->attribute_list - - while ($node) - print *(CK_ATTRIBUTE *)($node->data) - set $node = $node->next - end -end - -define __ock_print_node_type - if $arg1 == $OBJECT_MAP - print *((OBJECT_MAP *)($arg0)->value) - end - if $arg1 == $OBJECT - print *((OBJECT *)($arg0)->value) - end - if $arg1 == $SESSION - print *((SESSION *)($arg0)->value) - end -end - -define __ock_print_node - set $n = ($arg0) - set $loc = ($arg1) - - while ($loc > 1) - if ($loc & 1) - set $n = $n->right - else - set $n = $n->left - end - - set $loc = $loc >> 1 - printf " " - end - - if ($n->flags & 1) - printf "`- %d: (deleted node)\n", $arg1 - else - printf "`- %d: ", $arg1 - __ock_print_node_type $n $arg2 - end -end - -define __ock_dump_tree - set $size = ($arg0).size + 1 - set $i = 1 - - printf "tree: size %d, free nodes: %d\n", $arg0.size, ($arg0).free_nodes - while ($i < $size) - __ock_print_node ($arg0).top $i ($arg1) - set $i = $i + 1 - end -end - -define ock_dump_object_map - __ock_dump_tree object_map_btree $OBJECT_MAP -end - -define ock_dump_sess_btree - __ock_dump_tree sess_btree $SESSION -end - -define ock_dump_sess_obj_btree - __ock_dump_tree sess_obj_btree $OBJECT -end - -define ock_dump_priv_tok_obj_btree - __ock_dump_tree priv_token_obj_btree $OBJECT -end - -define ock_dump_publ_tok_obj_btree - __ock_dump_tree publ_token_obj_btree $OBJECT -end - -define dump_ec_key_token - set $tok = ($arg0) - printf "----------------------- HEADER SECTION -----------------------\n" - printf "Token ID: 0x%02X\n", $tok - printf "Token Version Number: 0x%02X\n", $tok[1] - printf "Length in bytes of token structure: 0x%02X%02X\n", $tok[2], $tok[3] - printf "----------------------- PRIVATE SECTION -----------------------\n" - set $priv = $tok[8] - printf "Section ID: 0x%02X\n", $priv - printf "\tX'20': ECC private key\n" - printf "Section version number: 0x%02X\n", $tok[9] - printf "Section len: 0x%02X%02X\n", $tok[10], $tok[11] - printf "Wrapping method: 0x%02X\n", $tok[12] - printf "\tX'00': Section is unencrypted (clear), X'01': AESKW, X'02: CBC\n" - printf "Hash method used for wrapping: 0x%02X\n", $tok[13] - printf "\tX'01': SHA-224, X'02': SHA-256\n" - printf "Key usage: 0x%02X\n", $tok[16] - printf "\tX'C0': Key agreement, X'80': Both signature gen & key agreement\n" - printf "\tX'00': Signature generation only, X'02': Translate allowed\n" - printf "Curve type: 0x%02X\n", $tok[17] - printf "\tX'00': Prime curve, X'01': Brainpool curve\n" - printf "Key format and security flag: 0x%02X\n", $tok[18] - printf "\tEncrypted internal ECC: X'08', " - printf "Unencrypted external ECC: X'40', " - printf "Encrypted external ECC: X'42'\n" - printf "Length of p in bits: 0x%02X%02X\n", $tok[20], $tok[21] - printf "\tX'00A0': Brainpool P-160\n" - printf "\tX'00C0': Prime P-192, Brainpol P-192\n" - printf "\tX'00E0': Brainpool P-224, Prime P-224\n" - printf "\tX'0100': Brainpool P-256, Prime P-256\n" - printf "\tX'0140': Brainpool P-320\n" - printf "\tX'0180': Prime P-384, Brainpool P-384\n" - printf "\tX'0200': Brainpool P-512\n" - printf "\tX'0209': Prime P-521\n" - printf "IBM associated data length in bytes: 0x%02X%02X\n", $tok[22], $tok[23] - printf "Master key verification pattern:\n\t" - set $i = 0 - while ($i < 8) - printf "%02X", $tok[24+$i] - set $i = $i+1 - end - printf "\n" - - printf "Associated data length: 0x%02X%02X\n", $tok[80], $tok[81] - printf "Length of formatted section in bytes: 0x%02X%02X\n", $tok[82], $tok[83] - printf "-------- Begin formatted section (include d) data --------\n" - set $dlen = $tok[83] - set $assclen = $tok[81] - set $i = 0 - while ($i < $dlen) - printf "%02X", $tok[84+$assclen+$i] - set $i = $i+1 - end - printf "\n-------- End formatted section data --------\n" - printf "----------------------- PUBLIC SECTION -----------------------\n" - set $privlen = $tok[11] - set $puboffset = $privlen+8 - printf "Section ID: 0x%02X\n", $tok[$puboffset] - printf "\tX'21': ECC public key\n" - printf "Section version number: 0x%02X\n", $tok[$puboffset+1] - printf "Section length: 0x%02X%02X\n", $tok[$puboffset+2], $tok[$puboffset+3] - printf "Curve type: 0x%02X\n", $tok[$puboffset+8] - printf "\tX'00': Prime curve, X'01': Brainpool curve\n" - printf "Length of p in bits: 0x%02X%02X\n", $tok[$puboffset+10], $tok[$puboffset+11] - printf "Length of public key q in bytes: 0x%02X%02X\n", $tok[$puboffset+12], $tok[$puboffset+13] - printf "-------- Begin q data --------\n" - set $qlen = $tok[$puboffset+13] - set $i = 0 - while ($i < $qlen) - printf "%02X", $tok[$puboffset+14+$i] - set $i = $i+1 - end - printf "\n-------- End q data --------\n" -end -document dump_ec_key_token -Print the Elliptic Curve key token generated by CSNDPKG. -end diff -Nru opencryptoki-3.18.0+dfsg/misc/opencryptoki.pc.in opencryptoki-3.20.0+dfsg/misc/opencryptoki.pc.in --- opencryptoki-3.18.0+dfsg/misc/opencryptoki.pc.in 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/misc/opencryptoki.pc.in 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,12 @@ +prefix=@prefix@ +exec_prefix=@exec_prefix@ +libdir=@libdir@/opencryptoki +stdlldir=@libdir@/opencryptoki/stdll +includedir=@includedir@/opencryptoki + +Name: Opencryptoki +Description: Opencryptoki PKCS#11 module +URL: https://github.com/opencryptoki/opencryptoki +Version: @VERSION@ +Cflags: -I${includedir} +Libs: -L${libdir} -lopencryptoki diff -Nru opencryptoki-3.18.0+dfsg/misc/rsa_parser.pl opencryptoki-3.20.0+dfsg/misc/rsa_parser.pl --- opencryptoki-3.18.0+dfsg/misc/rsa_parser.pl 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/misc/rsa_parser.pl 1970-01-01 01:00:00.000000000 +0100 @@ -1,1664 +0,0 @@ -#!/usr/bin/perl -# -# COPYRIGHT (c) International Business Machines Corp. 2011-2017 -# -# This program is provided under the terms of the Common Public License, -# version 1.0 (CPL-1.0). Any use, reproduction or distribution for this software -# constitutes recipient's acceptance of CPL-1.0 terms which can be found -# in the file LICENSE file or at https://opensource.org/licenses/cpl1.0.php -# -# This script parses the RSA test vectors found in $in_file -# and formats them for openCryptoki tests -# -# Fionnuala Gunter -# August 18, 2011 -# -# -# To run: -# download ftp://ftp.rsa.com/pub/rsalabs/tmp/pkcs1v15sign-vectors.tx -# ./rsa_parser.pl > rsa.h -# -# -#TODO: For some reason, there are extra blank lines printed... -# - -# constants -$max_tv = 300; # maximum number of test vectors to add to file -$sub_max = 3; # maximum number of messages/signatures per key pair -$count = 0; # current number of test vectors added to file -$in_file = "pkcs1v15sign-vectors.txt"; # test vector source - -# tmp -$string; - -# input -$example = "# Example \d+: A \d+-bit RSA key pair"; -$key = '# Private key'; -$modulus = '# Modulus: '; -$publicexponent = '# Public exponent: '; -$privateexponent = '# Exponent: '; -$prime1_ = '# Prime 1: '; -$prime2_ = '# Prime 2: '; -$exponent1 = '# Prime exponent 1: '; -$exponent2 = '# Prime exponent 2: '; -$coefficient = '# Coefficient: '; -$msgblock = "# PKCS#1 v1.5 signing of 20 random messages "; -$msgsighead = "# PKCS#1 v1.5 Signature Example $num_msg "; -$msghead = '# Message to be signed:'; -$sighead = '# Signature:'; - -# output -$begin_struct = "//ftp://ftp.rsa.com/pub/rsalabs/tmp/pkcs1v15sign-vectors.txt\n". - "struct RSA_PUBLISHED_TEST_VECTOR ". - "rsa_sha1_pkcs_sigver_published_tv[] = {\n"; -$end_struct = "};\n"; -$begin_ele = "\t{"; -$end_ele = "\t},\n"; -$begin_mod = "\t\t.mod = "; -$begin_pubexp = "\t\t.pub_exp = "; -$begin_privexp = "\t\t.priv_exp = "; -$begin_prime1 = "\t\t.prime1 = "; -$begin_prime2 = "\t\t.prime2 = "; -$begin_exp1 = "\t\t.exp1 = "; -$begin_exp2 = "\t\t.exp2 = "; -$begin_coef = "\t\t.coef = "; -$begin_msg = "\t\t.msg = "; -$begin_sig = "\t\t.sig = "; -$begin_modlen = "\t\t.mod_len = "; -$begin_pubexplen = "\t\t.pubexp_len = "; -$begin_privexplen = "\t\t.privexp_len = "; -$begin_prime1len = "\t\t.prime1_len = "; -$begin_prime2len = "\t\t.prime2_len = "; -$begin_exp1len = "\t\t.exp1_len = "; -$begin_exp2len = "\t\t.exp2_len = "; -$begin_coeflen = "\t\t.coef_len = "; -$begin_msglen = "\t\t.msg_len = "; -$begin_siglen = "\t\t.sig_len = "; - - -# giant block of generated tests that I copy-pasted here. -# this could be replaced with some functions that generate the data below -# TODO: CKM_CDMF_KEY_GEN doesn't seem to be supported by ICA, CCA or Soft, -# so those tests can be removed -$defheader = "#include \"pkcs11types.h\" -#define MAX_MODULUS_SIZE 256 -#define MAX_EXPONENT_SIZE 256 -#define MAX_MESSAGE_SIZE 512 -#define MAX_SIGNATURE_SIZE 512 -#define MAX_PRIME_SIZE 128 -#define MAX_COEFFICIENT_SIZE 128 -#define PKCS11_MAX_KEY_LEN 512 - - -struct RSA_GENERATED_TEST_VECTOR { - CK_ULONG modbits; - CK_ULONG publ_exp_len; - CK_BYTE publ_exp[4]; - CK_ULONG inputlen; - CK_MECHANISM keytype; - CK_ULONG keylen; -}; - -static struct RSA_GENERATED_TEST_VECTOR rsa_keywrap_generated_tv[] = { - { // 0 - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 1 - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 2 - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 3 - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 4 - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 5 - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 6 - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 64, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 7 - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 8 - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 9 - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 10 - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 11 - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 12 - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 13 - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 64, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 14 - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 15 - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 16 - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 17 - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 18 - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 19 - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 20 - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 64, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 21 - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0} - }, { // 22 - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 23 - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 24 - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 25 - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 26 - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 27 - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 64, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 28 - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 29 - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 30 - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 31 - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0} - }, { // 32 - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 33 - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 34 - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 64, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 35 - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 36 - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 37 - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 38 - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 39 - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 40 - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 41 - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 96, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 42 - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 43 - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 44 - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 45 - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 46 - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 47 - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 48 - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 96, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 49 - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 50 - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 51 - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 52 - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 53 - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 54 - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 55 - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 128, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 56 - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 57 - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 58 - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 59 - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 60 - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 61 - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 62 - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 128, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 63 - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 64 - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 65 - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 66 - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 67 - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 68 - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 69 - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 256, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 70 - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 71 - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 72 - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 73 - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 74 - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 75 - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 76 - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 256, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 77 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - },{ // 78 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 79 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 80 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 81 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 82 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 83 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 256, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 84 - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 85 - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 86 - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 87 - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 88 - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 89 - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 90 - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .keylen = 512, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 91 - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 92 - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 93 - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 94 - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 95 - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 96 - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - },{ // 97 - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .keylen = 512, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - }, { // 98 - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 1, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - },{ // 99 - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, { // 100 - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 8, - .keytype = {CKM_DES_KEY_GEN, 0, 0}, - }, { // 101 - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 24, - .keytype = {CKM_DES3_KEY_GEN, 0, 0}, - }, { // 102 - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 16, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 103 - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 32, - .keytype = {CKM_AES_KEY_GEN, 0, 0}, - }, { // 104 - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .keylen = 512, - .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - } - -}; - -static struct RSA_GENERATED_TEST_VECTOR rsa_generated_tv[] = { - { // tv[0] - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1, - }, { //tv[1] - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 53, - }, { //tv[2] - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { //tv[3] - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 53, - }, { //tv[4] - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x03, 0x00, 0x01 }, - .inputlen = 1, - }, { //tv[5] - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x03, 0x00, 0x01 }, - .inputlen = 53, - }, { //tv[6] - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1, - }, { //tv[7] - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 85, - }, { //tv[8] - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { //tv[9] - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 85, - }, { //tv[10] - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1, - }, { //tv[11] - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 85, - }, { //tv[12] - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1, - }, { //tv[13] - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 117, - }, { //tv[14] - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { //tv[15] - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 117, - }, { //tv[16] - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1, - }, { //tv[17] - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 117, - }, { //tv[18] - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1, - }, { //tv[19] - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 245, - }, { //tv[20] - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { //tv[21] - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 245, - }, { //tv[22] - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1, - }, { //tv[23] - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 245, - }, { //tv[24] - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1, - }, { //tv[25] - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 501, - }, { //tv[26] - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { //tv[27] - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 501, - }, { //tv[28] - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1, - }, { //tv[29] - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 501, - }, - - -}; - -static struct RSA_GENERATED_TEST_VECTOR rsa_x509_generated_tv[] = { - { // tv[0] - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1, - }, { // tv[1] - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 64, - }, { // tv[2] - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { // tv[3] - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 64, - }, { // tv[4] - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1, - }, { // tv[5] - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 64, - }, { // tv[6] - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1, - }, { // tv[7] - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 96, - }, { // tv[8] - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { // tv[9] - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 96, - }, { // tv[10] - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1, - }, { // tv[11] - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 96, - }, { // tv[12] - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1 - }, { // tv[13] - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 128, - }, { // tv[14] - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { // tv[15] - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 128, - }, { // tv[16] - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1 - }, { // tv[17] - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 128, - }, { // tv[18] - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1 - }, { // tv[19] - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 256, - }, { // tv[20] - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { // tv[21] - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 256, - }, { // tv[22] - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1 - }, { // tv[23] - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 256, - }, { // tv[24] - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 1 - }, { // tv[25] - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = { 0x03 }, - .inputlen = 512, - }, { // tv[26] - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 1, - }, { // tv[27] - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = { 0x00, 0x11 }, - .inputlen = 512, - }, { // tv[28] - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 1 - }, { // tv[29] - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = { 0x01, 0x00, 0x01 }, - .inputlen = 512, - } -}; - -struct GENERATED_TEST_SUITE_INFO { - const char *name; - unsigned int tvcount; - struct RSA_GENERATED_TEST_VECTOR *tv; - CK_MECHANISM mech; -}; - -#define NUM_OF_GENERATED_KEYWRAP_TESTSUITES 2 -struct GENERATED_TEST_SUITE_INFO generated_keywrap_test_suites[] = { - { - .name = \"RSA PKCS\", - .tvcount = 105, - .tv = rsa_keywrap_generated_tv, - .mech = {CKM_RSA_PKCS, 0, 0}, - }, { - .name = \"RSA X.509\", - .tvcount = 105, - .tv = rsa_keywrap_generated_tv, - .mech = {CKM_RSA_X_509, 0, 0}, - } -}; - - -#define NUM_OF_GENERATED_SIGVER_TESTSUITES 5 -struct GENERATED_TEST_SUITE_INFO generated_sigver_test_suites[] = { - { - .name = \"RSA PKCS\", - .tvcount = 30, - .tv = rsa_generated_tv, - .mech = {CKM_RSA_PKCS, 0, 0}, - }, { - .name = \"RSA SHA1 PKCS\", - .tvcount = 30, - .tv = rsa_generated_tv, - .mech = {CKM_SHA1_RSA_PKCS, 0, 0}, - }, { - .name = \"RSA MD2 PKCS\", - .tvcount = 30, - .tv = rsa_generated_tv, - .mech = {CKM_MD2_RSA_PKCS, 0, 0}, - }, { - .name = \"RSA MD5 PKCS\", - .tvcount = 30, - .tv = rsa_generated_tv, - .mech = {CKM_MD5_RSA_PKCS, 0 , 0}, - }, { - .name = \"RSA X.509\", - .tvcount = 30, - .tv = rsa_x509_generated_tv, - .mech = {CKM_RSA_X_509, 0 , 0}, - } -}; - -#define NUM_OF_GENERATED_CRYPTO_TESTSUITES 2 -struct GENERATED_TEST_SUITE_INFO generated_crypto_test_suites[] = { - { - .name = \"RSA PKCS\", - .tvcount = 30, - .tv = rsa_generated_tv, - .mech = {CKM_RSA_PKCS, 0, 0}, - }, { - .name = \"RSA X.509\", - .tvcount = 30, - .tv = rsa_x509_generated_tv, - .mech = {CKM_RSA_X_509, 0, 0}, - } -}; - -struct RSA_PUBLISHED_TEST_VECTOR { - CK_BYTE mod[MAX_MODULUS_SIZE]; // n - CK_ULONG mod_len; - CK_BYTE prime1[MAX_PRIME_SIZE]; // p - CK_ULONG prime1_len; - CK_BYTE prime2[MAX_PRIME_SIZE]; // q - CK_ULONG prime2_len; - CK_BYTE exp1[MAX_EXPONENT_SIZE]; // d % (p-1) - CK_ULONG exp1_len; - CK_BYTE exp2[MAX_EXPONENT_SIZE]; // d % (q-1) - CK_ULONG exp2_len; - CK_BYTE coef[MAX_COEFFICIENT_SIZE]; // (q^-1) % p - CK_ULONG coef_len; - CK_BYTE pub_exp[MAX_EXPONENT_SIZE]; // e - CK_ULONG pubexp_len; - CK_BYTE priv_exp[MAX_EXPONENT_SIZE]; // d - CK_ULONG privexp_len; - CK_BYTE msg[MAX_MESSAGE_SIZE]; - CK_ULONG msg_len; - CK_BYTE sig[MAX_SIGNATURE_SIZE]; - CK_ULONG sig_len; -};\n"; - -# vars - -@mod; -@pubexp; -@privexp; -@prime1; -@prime2; -@exp1; -@exp2; -@coef; -@msg; -@sig; - -$modlen = 0; -$pubexplen = 0; -$privexplen = 0; -$prime1len = 0; -$prime2len = 0; -$exp1len = 0; -$exp2len = 0; -$coeflen = 0; -$msglen = 0; -$siglen = 0; - -# open test vector file -# parse contents -# print results -open ($file, $in_file); -print $defheader; -print $begin_struct; -my $subcount; -while (<$file>) { - # parse key pair - if ($_ =~ $key){ - parse_keys(); - $subcount = 0; - } - # parse message - if ($_ =~ $msghead){ - #print "\n"; - parse_msg(); - } - # parse signature and print struct element - if ($_ =~ $sighead){ - #print "\n"; - parse_sig(); - if ($subcount < $sub_max){ - print_ele(); - $count++; - } - if ($count > $max_tv){ - last; - } - #$count++; - $subcount++; - } -} -print $end_struct; -print "\n"; - -$footer = "struct PUBLISHED_TEST_SUITE_INFO { - const char *name; - unsigned int tvcount; - struct RSA_PUBLISHED_TEST_VECTOR *tv; - CK_MECHANISM mech; - unsigned int result; -}; - -#define NUM_OF_PUBLISHED_TESTSUITES 1 -struct PUBLISHED_TEST_SUITE_INFO published_test_suites[] = { - { - .name = \"RSA SHA-1 PKCS v1.5\", - .tvcount = $count, - .tv = rsa_sha1_pkcs_sigver_published_tv, - .mech = {CKM_SHA1_RSA_PKCS, 0, 0}, - } - - -};"; - -print $footer; -close ($file); - -sub parse_keys(){ - while (<$file>){ - print "\n"; - # skip # ----- - if ($_ =~ m/^# -/){ - next; - } - - # skip " " - elsif (length($_) == 1 || length($_) == 2 || (!$_)){ - next; - } - - # parse modulus - elsif ($_ =~ $modulus){ - parse_mod(); - next; - } - - # parse public exponent - elsif ($_ =~ $publicexponent){ - parse_pubexp(); - next; - } - - # parse private exponent - elsif ($_ =~ $privateexponent){ - parse_privexp(); - next; - } - - # parse prime1 - elsif ($_ =~ $prime1_){ - parse_prime1(); - next; - } - - # parse prime2 - elsif ($_ =~ $prime2_){ - parse_prime2(); - next; - } - - # parse exponent1 - elsif ($_ =~ $exponent1){ - parse_exp1(); - next; - } - - # parse exponent2 - elsif ($_ =~ $exponent2){ - parse_exp2(); - next; - } - - # parse coefficient - elsif ($_ =~ $coefficient){ - parse_coef(); - last; - } - } -} - -# parse modulus -sub parse_mod(){ - @mod = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@mod, $string); - } - } - else { - $modlen = @mod; - last; - } - } -} - -# parse public exponent -sub parse_pubexp(){ - @pubexp = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@pubexp, $string); - } - } - else { - $pubexplen = @pubexp; - last; - } - } -} - -# parse private exponent -sub parse_privexp(){ - @privexp = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@privexp, $string); - } - } - else { - $privexplen = @privexp; - last; - } - } -} - -# parse prime 1 -sub parse_prime1(){ - @prime1 = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@prime1, $string); - } - } - else { - $prime1len = @prime1; - last; - } - } -} - -# parse prime 2 -sub parse_prime2(){ - @prime2 = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@prime2, $string); - } - } - else { - $prime2len = @prime2; - last; - } - } -} - -# parse exponent 1 -sub parse_exp1(){ - @exp1 = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@exp1, $string); - } - } - else { - $exp1len = @exp1; - last; - } - } -} - -# parse exponent 2 -sub parse_exp2(){ - @exp2 = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@exp2, $string); - } - } - else { - $exp2len = @exp2; - last; - } - } -} - -# parse coefficient -sub parse_coef(){ - @coef = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@coef, $string); - } - } - else { - $coeflen = @coef; - last; - } - } -} - -# parse message -sub parse_msg(){ - @msg = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@msg, $string); - } - } - else { - $msglen = @msg; - last; - } - } -} - -# parse signature -sub parse_sig(){ - @sig = (); - while (<$file>){ - if ($_ =~ m{\S+}){ - for (my $n = 0; ($n + 2) < length($_); $n+=3) { - $string = "0x".substr($_, $n, 2); - push(@sig, $string); - } - } - else { - $siglen = @sig; - last; - } - } -} - -# prints test vector -sub print_ele(){ - print $begin_ele; - print "\t/\/\ $count\n"; # new - print_mod(); - print_pubexp(); - print_privexp(); - print_prime1(); - print_prime2(); - print_exp1(); - print_exp2(); - print_coef(); - print_msg(); - print_sig(); - print $end_ele; -} - -# prints modulus -sub print_mod(){ - print $begin_mod; - print "\t { "; - for (my $n = 0; $n < $modlen; $n++){ - print $mod[$n]; - if ($n + 1 < $modlen){ - print ","; - } - if (($n + 1 < $modlen) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - } - print " },\n"; - print $begin_modlen; - print $modlen; - print ",\n"; -} - -# prints public exponent -sub print_pubexp(){ - print $begin_pubexp; - print " { "; - for (my $n = 0; $n < $pubexplen; $n++){ - print $pubexp[$n]; - if ($n + 1 < $pubexplen){ - print ","; - } - } - print " },\n"; - print $begin_pubexplen; - print $pubexplen; - print ",\n"; -} - -# prints private exponent -sub print_privexp(){ - print $begin_privexp; - print " { "; - for (my $n = 0; $n < $privexplen; $n++){ - print $privexp[$n]; - if ($n + 1 < $privexplen){ - print ","; - } - if (($n + 1 < $privexplen) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - - } - print " },\n"; - print $begin_privexplen; - print $privexplen; - print ",\n"; -} - -# prints prime 1 -sub print_prime1(){ - print $begin_prime1; - print " { "; - for (my $n = 0; $n < $prime1len; $n++){ - print $prime1[$n]; - if ($n + 1 < $prime1len){ - print ","; - } - if (($n + 1 < $prime1len) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - - } - print " },\n"; - print $begin_prime1len; - print $prime1len; - print ",\n"; -} - -# prints prime 2 -sub print_prime2(){ - print $begin_prime2; - print " { "; - for (my $n = 0; $n < $prime2len; $n++){ - print $prime2[$n]; - if ($n + 1 < $prime2len){ - print ","; - } - if (($n + 1 < $prime2len) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - - } - print " },\n"; - print $begin_prime2len; - print $prime2len; - print ",\n"; -} - -# prints exponent 1 -sub print_exp1(){ - print $begin_exp1; - print " { "; - for (my $n = 0; $n < $exp1len; $n++){ - print $exp1[$n]; - if ($n + 1 < $exp1len){ - print ","; - } - if (($n + 1 < $exp1len) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - - } - print " },\n"; - print $begin_exp1len; - print $exp1len; - print ",\n"; -} - -# prints exponent 2 -sub print_exp2(){ - print $begin_exp2; - print " { "; - for (my $n = 0; $n < $exp2len; $n++){ - print $exp2[$n]; - if ($n + 1 < $exp2len){ - print ","; - } - if (($n + 1 < $exp2len) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - - } - print " },\n"; - print $begin_exp2len; - print $exp2len; - print ",\n"; -} - -# prints coefficient -sub print_coef(){ - print $begin_coef; - print " { "; - for (my $n = 0; $n < $coeflen; $n++){ - print $coef[$n]; - if ($n + 1 < $coeflen){ - print ","; - } - if (($n + 1 < $coeflen) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - - } - print " },\n"; - print $begin_coeflen; - print $coeflen; - print ",\n"; -} - -# prints message -sub print_msg(){ - print $begin_msg; - print " { "; - for (my $n = 0; $n < $msglen; $n++){ - print $msg[$n]; - if ($n + 1 < $msglen){ - print ","; - } - if (($n + 1 < $msglen) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - - } - print " },\n"; - print $begin_msglen; - print $msglen; - print ",\n"; -} - -# prints signature -sub print_sig(){ - print $begin_sig; - print " { "; - for (my $n = 0; $n < $siglen; $n++){ - print $sig[$n]; - if ($n + 1 < $siglen){ - print ","; - } - if (($n + 1 < $siglen) && !(($n + 1) % 8)){ - print "\n\t\t\t\t"; - } - - } - print " },\n"; - print $begin_siglen; - print $siglen; - print ",\n"; -} diff -Nru opencryptoki-3.18.0+dfsg/misc/test_mech_list.c opencryptoki-3.20.0+dfsg/misc/test_mech_list.c --- opencryptoki-3.18.0+dfsg/misc/test_mech_list.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/misc/test_mech_list.c 1970-01-01 01:00:00.000000000 +0100 @@ -1,34 +0,0 @@ -/* - * COPYRIGHT (c) International Business Machines Corp. 2005-2017 - * - * This program is provided under the terms of the Common Public License, - * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this - * software constitutes recipient's acceptance of CPL-1.0 terms which can be - * found in the file LICENSE file or at - * https://opensource.org/licenses/cpl1.0.php - */ - -/** - * This is something like what you can expect openCryptoki to do when - * it requests a mechanism list from your library. - */ - -#include -#include "mech_types.h" - -extern void generate_pkcs11_mech_list(struct mech_list *head); - -int main(int argc, char *argv[]) -{ - struct mech_list head; - struct mech_list *item; - generate_pkcs11_mech_list(&head); - item = head.next; - while (item) { - struct mech_list *next; - next = item->next; - printf("Mechanism type: [%.8x]\n", item->element.mech_type); - free(item); - item = next; - } -} diff -Nru opencryptoki-3.18.0+dfsg/opencryptoki_tok.map opencryptoki-3.20.0+dfsg/opencryptoki_tok.map --- opencryptoki-3.18.0+dfsg/opencryptoki_tok.map 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/opencryptoki_tok.map 2023-02-13 09:22:42.000000000 +0100 @@ -65,6 +65,7 @@ SC_WaitForSlotEvent; SC_WrapKey; SC_IBM_ReencryptSingle; + SC_SessionCancel; ST_Initialize; local: *; }; diff -Nru opencryptoki-3.18.0+dfsg/README.md opencryptoki-3.20.0+dfsg/README.md --- opencryptoki-3.18.0+dfsg/README.md 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/README.md 2023-02-13 09:22:42.000000000 +0100 @@ -3,13 +3,13 @@ # openCryptoki -Package version 3.18 +Package version 3.20 Please see [ChangeLog](ChangeLog) for release specific information. ## OVERVIEW -openCryptoki version 3.18 implements the PKCS#11 specification version 3.0. +openCryptoki version 3.20 implements the PKCS#11 specification version 3.0. This package includes several cryptographic tokens: CCA, ICA, TPM , SWToken, ICSF and EP11. @@ -17,6 +17,10 @@ For a more in-depth overview of openCryptoki, please refer to manual [openCryptoki - An Open Source Implementation of PKCS #11](https://www.ibm.com/docs/en/linux-on-systems?topic=11-version-317) +**Note:** The TPM token is deprecated, because it supports only TPM version 1.2. +Does not work with TPM version 2.0. We plan to remove the TPM token in a future +openCryptoki release or version. + ## REQUIREMENTS: - IBM ICA - requires libica library version 3.3.0 or higher for accessing ICA @@ -25,7 +29,8 @@ - IBM CCA - requires IBM XCrypto CEX3C card (or higher) and the CEX3C host libraries and tools version 4.1 (or higher). -- TPM - requires a TPM, TPM tools, and TCG software stack. +- TPM (**deprecated**) - requires a TPM, TPM tools, and TCG software stack. +Supports TPM version 1.2 only. - SWToken - The software token uses OpenSSL version 1.1.1 or higher. @@ -48,6 +53,14 @@ $ ./bootstrap.sh ``` +** Note: ** This package used the `AX_PROG_CC_FOR_BUILD` autoconf macro +from the autoconf archive to support cross compiler builds. +If your system does not provide this macro, you might need to install the +`autoconf-archive` package or download the macro and place it into the +`m4` directory. +See [https://www.gnu.org/software/autoconf-archive/ax_prog_cc_for_build.html](https://www.gnu.org/software/autoconf-archive/ax_prog_cc_for_build.html) +for a link to the latest version of `ax_prog_cc_for_build.m4`. + 2. Configure the source code by typing: ``` @@ -84,6 +97,10 @@ ``` $ make ``` + **Note:** Do not specify `prefix=/foo/bar`, `libdir=/foo/bar` with + the `make` invocation. Specify them with `configure` instead. Specifying + them with `make` is not supported by the openCryptoki package and may + produce unexpected results! 4. openCryptoki defaults to be usable by anyone who is in the group ``pkcs11``. Add the pkcs11 group before installing it, by typing as root the command: @@ -96,7 +113,7 @@ be in pkcs11 group): ``` - # usermod -G pkcs11 + # usermod -a -G pkcs11 ``` 5. Type `make install` (as root) to install the programs and any data files and diff -Nru opencryptoki-3.18.0+dfsg/rpm/opencryptoki.spec opencryptoki-3.20.0+dfsg/rpm/opencryptoki.spec --- opencryptoki-3.18.0+dfsg/rpm/opencryptoki.spec 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/rpm/opencryptoki.spec 2023-02-13 09:22:42.000000000 +0100 @@ -2,7 +2,7 @@ Name: opencryptoki Summary: Implementation of the PKCS#11 (Cryptoki) specification v3.0 -Version: 3.18.0 +Version: 3.20.0 Release: 1%{?dist} License: CPL Group: System Environment/Base @@ -10,13 +10,15 @@ Source: https://github.com/%{name}/%{name}/archive/v%{version}.tar.gz#/%{name}-%{version}.tar.gz Requires(pre): coreutils +BuildRequires: gcc BuildRequires: openssl-devel >= 1.1.1 BuildRequires: trousers-devel BuildRequires: openldap-devel -BuildRequires: autoconf automake libtool +BuildRequires: autoconf automake libtool autoconf-archive BuildRequires: bison flex -BuildRequires: systemd +BuildRequires: systemd-devel BuildRequires: libitm-devel +BuildRequires: make %ifarch s390 s390x BuildRequires: libica-devel >= 3.3 %endif @@ -232,18 +234,27 @@ %doc ChangeLog FAQ README.md %doc doc/opencryptoki-howto.md %doc doc/README.token_data +%doc doc/policy-example.conf +%doc doc/strength-example.conf %dir %{_sysconfdir}/%{name} %config(noreplace) %{_sysconfdir}/%{name}/%{name}.conf +%attr(0640, root, pkcs11) %config(noreplace) %{_sysconfdir}/%{name}/strength.conf +%attr(0640, root, pkcs11) %config(noreplace) %{_sysconfdir}/%{name}/p11sak_defined_attrs.conf %{_prefix}/lib/tmpfiles.d/%{name}.conf %{_unitdir}/pkcsslotd.service %{_sbindir}/pkcsconf %{_sbindir}/pkcsslotd %{_sbindir}/p11sak %{_sbindir}/pkcstok_migrate +%{_sbindir}/pkcsstats %{_mandir}/man1/pkcsconf.1* %{_mandir}/man1/p11sak.1* %{_mandir}/man1/pkcstok_migrate.1* +%{_mandir}/man1/pkcsstats.1* %{_mandir}/man5/%{name}.conf.5* +%{_mandir}/man5/p11sak_defined_attrs.conf.5* +%{_mandir}/man5/policy.conf.5* +%{_mandir}/man5/strength.conf.5* %{_mandir}/man7/%{name}.7* %{_mandir}/man8/pkcsslotd.8* %{_libdir}/opencryptoki/methods @@ -271,6 +282,7 @@ %files devel %{_includedir}/%{name}/ +%{_libdir}/pkgconfig/%{name}.pc %files swtok %{_libdir}/opencryptoki/stdll/libpkcs11_sw.* @@ -301,6 +313,7 @@ %files ccatok %doc doc/README.cca_stdll +%config(noreplace) %{_sysconfdir}/%{name}/ccatok.conf %{_sbindir}/pkcscca %{_mandir}/man1/pkcscca.1* %{_libdir}/opencryptoki/stdll/libpkcs11_cca.* diff -Nru opencryptoki-3.18.0+dfsg/testcases/ciconfig.sh opencryptoki-3.20.0+dfsg/testcases/ciconfig.sh --- opencryptoki-3.18.0+dfsg/testcases/ciconfig.sh 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/ciconfig.sh 2023-02-13 09:22:42.000000000 +0100 @@ -2,9 +2,15 @@ OCKCONFDIR="$1" EPCONFDIR="$2" +CCACONFDIR="$3" LATESTCEXP="CEX7P" +CCA_SYM_MKVP="5776993D2741EB4A" +CCA_AES_MKVP="E9A49A58CD039BED" +CCA_APKA_MKVP="5F2F27AAA2D59B4A" +EP11_WKVP="8b991263e3a8f4e4be0d5ec8f0a4df9e" + USENEWFORMAT=/bin/false # Usage: addslot slot-num stdll slot-name [confname] @@ -16,7 +22,7 @@ tokname = $3 EOF if $USENEWFORMAT; then - echo "tokversion = 3.12" >> "${OCKCONFDIR}/opencryptoki.conf" + echo "tokversion = 3.12" >> "${OCKCONFDIR}/opencryptoki.conf" fi if [ "x$4" != "x" ]; then echo "confname = $4" >> "${OCKCONFDIR}/opencryptoki.conf" @@ -32,22 +38,35 @@ EOF } -# Usage: genlatestep11cfg num +# Usage: genlatestep11cfg num configline # Return: 0 if successful function genlatestep11cfg() { local res=1 - lszcrypt | grep "$LATESTCEXP" | perl -ne '/(\d+)\.(\d+)\s.*/ && print "0x$1 0x$2\n"' > tmp.apqns + lszcrypt | grep "$LATESTCEXP" | perl -ne '/([0-9a-fA-F]+)\.([0-9a-fA-F]+)\s.*/ && print "0x$1 0x$2\n"' > tmp.apqns if test -s tmp.apqns; then - echo "APQN_WHITELIST" > "${EPCONFDIR}/ep11tok${1}.conf" - cat tmp.apqns >> "${EPCONFDIR}/ep11tok${1}.conf" - echo "END" >> "${EPCONFDIR}/ep11tok${1}.conf" - res=0 + echo "${2}" > "${EPCONFDIR}/ep11tok${1}.conf" + echo "APQN_WHITELIST" >> "${EPCONFDIR}/ep11tok${1}.conf" + cat tmp.apqns >> "${EPCONFDIR}/ep11tok${1}.conf" + echo "END" >> "${EPCONFDIR}/ep11tok${1}.conf" + res=0 fi rm -f tmp.apqns return $res } +# Usage: genccamkvpcfg num +function genccamkvpcfg() { + cat < "${CCACONFDIR}/ccatok${1}.conf" +version cca-0 +EXPECTED_MKVPS { + SYM = "$CCA_SYM_MKVP" + AES = "$CCA_AES_MKVP" + APKA = "$CCA_APKA_MKVP" +} +EOF +} + if test $(($(date +%j)%2)) == 1; then USENEWFORMAT=/bin/true echo "Using FIPS compliant token store" @@ -56,7 +75,7 @@ fi # initialize opencryptoki.conf -echo "version opencryptoki-3.16" > "${OCKCONFDIR}/opencryptoki.conf" +echo "version opencryptoki-3.20" > "${OCKCONFDIR}/opencryptoki.conf" # enable full statistics echo "statistics (on,implicit,internal)" >> "${OCKCONFDIR}/opencryptoki.conf" @@ -66,7 +85,8 @@ addslot 11 libpkcs11_ica.so ica1 # CCA token -addslot 20 libpkcs11_cca.so cca0 +genccamkvpcfg 20 +addslot 20 libpkcs11_cca.so cca0 ccatok20.conf addslot 21 libpkcs11_cca.so cca1 # SW token @@ -76,7 +96,8 @@ # EP11 token # 0: # APQN_ANY -genep11cfg 40 "" +# EXPECTED_WKVP "wkvp" +genep11cfg 40 "EXPECTED_WKVP \"$EP11_WKVP\"" addslot 40 libpkcs11_ep11.so ep0 ep11tok40.conf # 1: @@ -105,13 +126,8 @@ genep11cfg 44 "DIGEST_LIBICA OFF" addslot 44 libpkcs11_ep11.so ep4 ep11tok44.conf -# 5: +# 5: latest (CEX7 only) # PKEY_MODE ENABLE4NONEXTR -# APQN_ANY -genep11cfg 45 "PKEY_MODE ENABLE4NONEXTR" -addslot 45 libpkcs11_ep11.so ep5 ep11tok45.conf - -# 6: latest -if genlatestep11cfg 46; then - addslot 46 libpkcs11_ep11.so ep6 ep11tok46.conf +if genlatestep11cfg 45 "PKEY_MODE ENABLE4NONEXTR"; then + addslot 45 libpkcs11_ep11.so ep5 ep11tok45.conf fi diff -Nru opencryptoki-3.18.0+dfsg/testcases/common/common.c opencryptoki-3.20.0+dfsg/testcases/common/common.c --- opencryptoki-3.18.0+dfsg/testcases/common/common.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/common/common.c 2023-02-13 09:22:42.000000000 +0100 @@ -167,20 +167,21 @@ /** Create an AES key handle with given value **/ CK_RV create_AESKey(CK_SESSION_HANDLE session, CK_BBOOL extractable, unsigned char key[], unsigned char key_len, - CK_OBJECT_HANDLE * h_key) + CK_KEY_TYPE keyType, CK_OBJECT_HANDLE * h_key) { CK_RV rc; CK_BBOOL true = TRUE; CK_BBOOL false = FALSE; CK_OBJECT_CLASS keyClass = CKO_SECRET_KEY; - CK_KEY_TYPE keyType = CKK_AES; + CK_BBOOL pkeyextractable = !extractable; CK_ATTRIBUTE keyTemplate[] = { {CKA_EXTRACTABLE, &extractable, sizeof(CK_BBOOL)}, {CKA_CLASS, &keyClass, sizeof(keyClass)}, {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, {CKA_ENCRYPT, &true, sizeof(true)}, {CKA_TOKEN, &false, sizeof(false)}, - {CKA_VALUE, key, key_len} + {CKA_VALUE, key, key_len}, + {CKA_IBM_PROTKEY_EXTRACTABLE, &pkeyextractable, sizeof(CK_BBOOL)}, }; CK_ULONG keyTemplate_len = sizeof(keyTemplate) / sizeof(CK_ATTRIBUTE); @@ -200,9 +201,11 @@ CK_ULONG key_len, CK_BBOOL extractable, CK_MECHANISM * mechkey, CK_OBJECT_HANDLE * h_key) { + CK_BBOOL pkeyextractable = !extractable; CK_ATTRIBUTE key_gen_tmpl[] = { {CKA_EXTRACTABLE, &extractable, sizeof(CK_BBOOL)}, - {CKA_VALUE_LEN, &key_len, sizeof(CK_ULONG)} + {CKA_VALUE_LEN, &key_len, sizeof(CK_ULONG)}, + {CKA_IBM_PROTKEY_EXTRACTABLE, &pkeyextractable, sizeof(CK_BBOOL)}, }; CK_ULONG key_gen_tmpl_len = sizeof(key_gen_tmpl) / sizeof(CK_ATTRIBUTE); @@ -536,8 +539,7 @@ CK_ULONG params_len, CK_BYTE privatekey[], CK_ULONG privatekey_len, - CK_BYTE pubkey[], - CK_ULONG pubkey_len, CK_OBJECT_HANDLE * priv_key, + CK_OBJECT_HANDLE * priv_key, CK_BBOOL extractable) { @@ -558,11 +560,9 @@ {CKA_SUBJECT, subject, 0}, {CKA_ID, id, sizeof(id)}, {CKA_SENSITIVE, &true, sizeof(true)}, - {CKA_DECRYPT, &true, sizeof(true)}, {CKA_SIGN, &true, sizeof(true)}, {CKA_DERIVE, &true, sizeof(true)}, {CKA_EC_PARAMS, params, params_len}, - {CKA_EC_POINT, pubkey, pubkey_len}, {CKA_VALUE, privatekey, privatekey_len}, {CKA_EXTRACTABLE, &extractable, sizeof(CK_BBOOL)} }; @@ -595,7 +595,6 @@ {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, {CKA_TOKEN, &true, sizeof(true)}, {CKA_LABEL, label, sizeof(label)}, - {CKA_ENCRYPT, &true, sizeof(true)}, {CKA_VERIFY, &true, sizeof(true)}, {CKA_DERIVE, &true, sizeof(true)}, {CKA_EC_PARAMS, params, params_len}, @@ -615,21 +614,22 @@ /** Create an IBM Dilithium private key using private values **/ CK_RV create_DilithiumPrivateKey(CK_SESSION_HANDLE session, - CK_BYTE rho[], CK_ULONG rho_len, - CK_BYTE seed[], CK_ULONG seed_len, - CK_BYTE tr[], CK_ULONG tr_len, - CK_BYTE s1[], CK_ULONG s1_len, - CK_BYTE s2[], CK_ULONG s2_len, - CK_BYTE t0[], CK_ULONG t0_len, - CK_BYTE t1[], CK_ULONG t1_len, - CK_OBJECT_HANDLE * priv_key) + CK_BYTE pkcs8[], CK_ULONG pkcs8_len, + CK_ULONG keyform, + CK_BYTE rho[], CK_ULONG rho_len, + CK_BYTE seed[], CK_ULONG seed_len, + CK_BYTE tr[], CK_ULONG tr_len, + CK_BYTE s1[], CK_ULONG s1_len, + CK_BYTE s2[], CK_ULONG s2_len, + CK_BYTE t0[], CK_ULONG t0_len, + CK_BYTE t1[], CK_ULONG t1_len, + CK_OBJECT_HANDLE * priv_key) { CK_OBJECT_CLASS class = CKO_PRIVATE_KEY; CK_KEY_TYPE keyType = CKK_IBM_PQC_DILITHIUM; CK_UTF8CHAR label[] = "A Dilithium private key object"; CK_BYTE subject[] = {0}; CK_BYTE id[] = { 123 }; - CK_ULONG keyform = IBM_DILITHIUM_KEYFORM_ROUND2; CK_RV rc; CK_BBOOL true = TRUE; @@ -652,13 +652,32 @@ {CKA_IBM_DILITHIUM_T1, t1, t1_len}, {CKA_IBM_DILITHIUM_KEYFORM, &keyform, sizeof(keyform)}, }; + CK_ATTRIBUTE template_pkcs8[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, + {CKA_TOKEN, &true, sizeof(true)}, + {CKA_PRIVATE, &true, sizeof(true)}, + {CKA_LABEL, label, sizeof(label)}, + {CKA_SUBJECT, subject, 0}, + {CKA_ID, id, sizeof(id)}, + {CKA_SENSITIVE, &true, sizeof(true)}, + {CKA_SIGN, &true, sizeof(true)}, + {CKA_VALUE, pkcs8, pkcs8_len}, + }; // create key - rc = funcs->C_CreateObject(session, template, - sizeof(template) / sizeof(CK_ATTRIBUTE), - priv_key); + if (pkcs8_len > 0) + rc = funcs->C_CreateObject(session, template_pkcs8, + sizeof(template_pkcs8) / sizeof(CK_ATTRIBUTE), + priv_key); + else + rc = funcs->C_CreateObject(session, template, + sizeof(template) / sizeof(CK_ATTRIBUTE), + priv_key); if (rc != CKR_OK) { - if (is_rejected_by_policy(rc, session)) + if (rc == CKR_KEY_SIZE_RANGE) + testcase_notice("C_CreateObject rc=%s", p11_get_ckr(rc)); + else if (is_rejected_by_policy(rc, session)) rc = CKR_POLICY_VIOLATION; else testcase_error("C_CreateObject rc=%s", p11_get_ckr(rc)); @@ -669,16 +688,17 @@ /** Create an IBM Dilithium public key using (rho, t1) **/ CK_RV create_DilithiumPublicKey(CK_SESSION_HANDLE session, - CK_BYTE rho[], CK_ULONG rho_len, - CK_BYTE t1[], CK_ULONG t1_len, - CK_OBJECT_HANDLE * publ_key) + CK_BYTE spki[], CK_ULONG spki_len, + CK_ULONG keyform, + CK_BYTE rho[], CK_ULONG rho_len, + CK_BYTE t1[], CK_ULONG t1_len, + CK_OBJECT_HANDLE * publ_key) { CK_RV rc; CK_OBJECT_CLASS class = CKO_PUBLIC_KEY; CK_KEY_TYPE keyType = CKK_IBM_PQC_DILITHIUM; CK_UTF8CHAR label[] = "A Dilithium public key object"; CK_BBOOL true = TRUE; - CK_ULONG keyform = IBM_DILITHIUM_KEYFORM_ROUND2; CK_ATTRIBUTE template[] = { {CKA_CLASS, &class, sizeof(class)}, {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, @@ -689,13 +709,147 @@ {CKA_IBM_DILITHIUM_T1, t1, t1_len}, {CKA_IBM_DILITHIUM_KEYFORM, &keyform, sizeof(keyform)}, }; + CK_ATTRIBUTE template_spki[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, + {CKA_TOKEN, &true, sizeof(true)}, + {CKA_LABEL, label, sizeof(label)}, + {CKA_VERIFY, &true, sizeof(true)}, + {CKA_VALUE, spki, spki_len}, + }; // create key - rc = funcs->C_CreateObject(session, template, - sizeof(template) / sizeof(CK_ATTRIBUTE), - publ_key); + if (spki_len > 0) + rc = funcs->C_CreateObject(session, template_spki, + sizeof(template_spki) / sizeof(CK_ATTRIBUTE), + publ_key); + else + rc = funcs->C_CreateObject(session, template, + sizeof(template) / sizeof(CK_ATTRIBUTE), + publ_key); if (rc != CKR_OK) { - if (is_rejected_by_policy(rc, session)) + if (rc == CKR_KEY_SIZE_RANGE) + testcase_notice("C_CreateObject rc=%s", p11_get_ckr(rc)); + else if (is_rejected_by_policy(rc, session)) + rc = CKR_POLICY_VIOLATION; + else + testcase_error("C_CreateObject rc=%s", p11_get_ckr(rc)); + } + + return rc; +} + +/** Create an IBM Kyber private key using private values **/ +CK_RV create_KyberPrivateKey(CK_SESSION_HANDLE session, + CK_BYTE pkcs8[], CK_ULONG pkcs8_len, + CK_ULONG keyform, + CK_BYTE sk[], CK_ULONG sk_len, + CK_BYTE pk[], CK_ULONG pk_len, + CK_OBJECT_HANDLE * priv_key) +{ + CK_OBJECT_CLASS class = CKO_PRIVATE_KEY; + CK_KEY_TYPE keyType = CKK_IBM_PQC_KYBER; + CK_UTF8CHAR label[] = "A Kyber private key object"; + CK_BYTE subject[] = {0}; + CK_BYTE id[] = { 123 }; + CK_RV rc; + + CK_BBOOL true = TRUE; + CK_ATTRIBUTE template[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, + {CKA_TOKEN, &true, sizeof(true)}, + {CKA_PRIVATE, &true, sizeof(true)}, + {CKA_LABEL, label, sizeof(label)}, + {CKA_SUBJECT, subject, 0}, + {CKA_ID, id, sizeof(id)}, + {CKA_SENSITIVE, &true, sizeof(true)}, + {CKA_SIGN, &true, sizeof(true)}, + {CKA_DERIVE, &true, sizeof(true)}, + {CKA_IBM_KYBER_SK, sk, sk_len}, + {CKA_IBM_KYBER_PK, pk, pk_len}, + {CKA_IBM_KYBER_KEYFORM, &keyform, sizeof(keyform)}, + }; + CK_ATTRIBUTE template_pkcs8[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, + {CKA_TOKEN, &true, sizeof(true)}, + {CKA_PRIVATE, &true, sizeof(true)}, + {CKA_LABEL, label, sizeof(label)}, + {CKA_SUBJECT, subject, 0}, + {CKA_ID, id, sizeof(id)}, + {CKA_SENSITIVE, &true, sizeof(true)}, + {CKA_SIGN, &true, sizeof(true)}, + {CKA_DERIVE, &true, sizeof(true)}, + {CKA_VALUE, pkcs8, pkcs8_len}, + }; + + // create key + if (pkcs8_len > 0) + rc = funcs->C_CreateObject(session, template_pkcs8, + sizeof(template_pkcs8) / sizeof(CK_ATTRIBUTE), + priv_key); + else + rc = funcs->C_CreateObject(session, template, + sizeof(template) / sizeof(CK_ATTRIBUTE), + priv_key); + if (rc != CKR_OK) { + if (rc == CKR_KEY_SIZE_RANGE) + testcase_notice("C_CreateObject rc=%s", p11_get_ckr(rc)); + else if (is_rejected_by_policy(rc, session)) + rc = CKR_POLICY_VIOLATION; + else + testcase_error("C_CreateObject rc=%s", p11_get_ckr(rc)); + } + + return rc; +} + +/** Create an IBM Kyber public key using public values **/ +CK_RV create_KyberPublicKey(CK_SESSION_HANDLE session, + CK_BYTE spki[], CK_ULONG spki_len, + CK_ULONG keyform, + CK_BYTE pk[], CK_ULONG pk_len, + CK_OBJECT_HANDLE * publ_key) +{ + CK_RV rc; + CK_OBJECT_CLASS class = CKO_PUBLIC_KEY; + CK_KEY_TYPE keyType = CKK_IBM_PQC_KYBER; + CK_UTF8CHAR label[] = "A Kyber public key object"; + CK_BBOOL true = TRUE; + CK_ATTRIBUTE template[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, + {CKA_TOKEN, &true, sizeof(true)}, + {CKA_LABEL, label, sizeof(label)}, + {CKA_VERIFY, &true, sizeof(true)}, + {CKA_DERIVE, &true, sizeof(true)}, + {CKA_IBM_KYBER_PK, pk, pk_len}, + {CKA_IBM_KYBER_KEYFORM, &keyform, sizeof(keyform)}, + }; + CK_ATTRIBUTE template_spki[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, + {CKA_TOKEN, &true, sizeof(true)}, + {CKA_LABEL, label, sizeof(label)}, + {CKA_VERIFY, &true, sizeof(true)}, + {CKA_DERIVE, &true, sizeof(true)}, + {CKA_VALUE, spki, spki_len}, + }; + + // create key + if (spki_len > 0) + rc = funcs->C_CreateObject(session, template_spki, + sizeof(template_spki) / sizeof(CK_ATTRIBUTE), + publ_key); + else + rc = funcs->C_CreateObject(session, template, + sizeof(template) / sizeof(CK_ATTRIBUTE), + publ_key); + if (rc != CKR_OK) { + if (rc == CKR_KEY_SIZE_RANGE) + testcase_notice("C_CreateObject rc=%s", p11_get_ckr(rc)); + else if (is_rejected_by_policy(rc, session)) rc = CKR_POLICY_VIOLATION; else testcase_error("C_CreateObject rc=%s", p11_get_ckr(rc)); @@ -1227,7 +1381,10 @@ CK_FLAGS flags; CK_BBOOL rv; CK_RV rc; - CK_RV(*pfoo) (); + CK_RV(*getfunclist)(CK_FUNCTION_LIST **funcs); + CK_RV(*getinterfacelist)(CK_INTERFACE_PTR interfaces, CK_ULONG *count); + CK_RV(*getinterface)(CK_UTF8CHAR_PTR name, CK_VERSION_PTR version, + CK_INTERFACE_PTR_PTR interface, CK_FLAGS flags); char *e; char *f = "libopencryptoki.so"; CK_ULONG nmemb = 0; @@ -1242,21 +1399,21 @@ if (pkcs11lib == NULL) goto ret; - *(void **)(&pfoo) = dlsym(pkcs11lib, "C_GetFunctionList"); - if (pfoo == NULL) + *(void **)(&getfunclist) = dlsym(pkcs11lib, "C_GetFunctionList"); + if (getfunclist == NULL) goto ret; - rc = pfoo(&funcs); + rc = getfunclist(&funcs); if (rc != CKR_OK) { testcase_error("C_GetFunctionList rc=%s", p11_get_ckr(rc)); goto ret; } - *(void **)(&pfoo) = dlsym(pkcs11lib, "C_GetInterfaceList"); - if (pfoo == NULL) { + *(void **)(&getinterfacelist) = dlsym(pkcs11lib, "C_GetInterfaceList"); + if (getinterfacelist == NULL) { goto ret; } - rc = pfoo(NULL, &nmemb); + rc = getinterfacelist(NULL, &nmemb); if (rc != CKR_OK) { testcase_error("C_GetInterfaceList rc=%s", p11_get_ckr(rc)); goto ret; @@ -1265,20 +1422,20 @@ if (ifs == NULL) { goto ret; } - rc = pfoo(ifs, &nmemb); + rc = getinterfacelist(ifs, &nmemb); if (rc != CKR_OK) { testcase_error("C_GetInterfaceList rc=%s", p11_get_ckr(rc)); goto ret; } - *(void **)(&pfoo) = dlsym(pkcs11lib, "C_GetInterface"); - if (pfoo == NULL) { + *(void **)(&getinterface) = dlsym(pkcs11lib, "C_GetInterface"); + if (getinterface == NULL) { goto ret; } version.major = 0x03; version.minor = 0x00; flags = CKF_INTERFACE_FORK_SAFE; - rc = pfoo((CK_UTF8CHAR *)"PKCS 11", &version, &interface, flags); + rc = getinterface((CK_UTF8CHAR *)"PKCS 11", &version, &interface, flags); if (rc != CKR_OK) { testcase_error("C_GetInterface rc=%s", p11_get_ckr(rc)); goto ret; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/abfunc.c opencryptoki-3.20.0+dfsg/testcases/crypto/abfunc.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/abfunc.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/abfunc.c 2023-02-13 09:22:42.000000000 +0100 @@ -597,7 +597,7 @@ /// Test functions -CK_RV do_CheckMechanismInfo() +CK_RV do_CheckMechanismInfo(void) { CK_IBM_ATTRIBUTEBOUND_WRAP_PARAMS params = { .hSignVerifyKey = CK_INVALID_HANDLE @@ -905,7 +905,7 @@ CK_IBM_ATTRIBUTEBOUND_WRAP_PARAMS params; CK_MECHANISM mech = {CKM_IBM_ATTRIBUTEBOUND_WRAP, ¶ms, sizeof(params)}; params.hSignVerifyKey = *(config[i].signingkey); - testcase_begin("AB Wrap/Unwrap test %d", i); + testcase_begin("AB Wrap/Unwrap test %u", i); testcase_new_assertion(); wrappedkeylen = sizeof(wrappedkey); rc = funcs->C_WrapKey(session, &mech, *(config[i].wrappingkey), @@ -1109,7 +1109,7 @@ } } -void testdriver() +void testdriver(void) { CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; CK_ULONG user_pin_len; @@ -1191,6 +1191,8 @@ } } else { rc = 0; + testcase_begin("%s\n", __func__); + testcase_skip("%s only supported on the EP11 token.\n", argv[0]); } funcs->C_Finalize(NULL); diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/aes_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/aes_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/aes_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/aes_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -69,17 +69,29 @@ goto testcase_cleanup; } + /* Skip tests if pkey = false, but the slot doesn't support CKM_AES_XTS */ + if (is_ep11_token(slot_id) && tsuite->mech.mechanism == CKM_AES_XTS && pkey == FALSE) { + testcase_skip("Slot supports AES-XTS only for protected keys.\n"); + goto testcase_cleanup; + } /** iterate over test key sizes **/ for (i = 0; i < 3; i++) { + if (tsuite->mech.mechanism == CKM_AES_XTS && key_lens[i] == 24) + continue; - testcase_begin("%s Encryption/Decryption with key len=%ld and pkey=%X.", + testcase_begin("%s Encryption/Decryption with key len=%lu and pkey=%X.", tsuite->name, key_lens[i], pkey); + /** set crypto mech **/ + mech = tsuite->mech; + /** generate key **/ - mechkey = aes_keygen; - rc = generate_AESKey(session, key_lens[i], !pkey, - &mechkey, &h_key); + mechkey = mech.mechanism == CKM_AES_XTS ? aes_xts_keygen : aes_keygen; + rc = generate_AESKey(session, + mech.mechanism == CKM_AES_XTS ? key_lens[i] * 2 : + key_lens[i], + !pkey, &mechkey, &h_key); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { testcase_skip("AES key generation is not allowed by policy"); @@ -101,9 +113,6 @@ for (j = 0; j < orig_len; j++) original[j] = j % 255; - /** set crypto mech **/ - mech = tsuite->mech; - /** single encryption **/ rc = funcs->C_EncryptInit(session, &mech, h_key); if (rc != CKR_OK) { @@ -142,13 +151,13 @@ if (decrypt_len != orig_len) { testcase_fail("decrypted data length does not " "match original data length.\nexpected " - "length=%ld, but found length=%ld\n", + "length=%lu, but found length=%lu\n", orig_len, decrypt_len); } else if (memcmp(decrypt, original, orig_len)) { testcase_fail("decrypted data does not match " "original data"); } else { testcase_pass("%s Encryption/Decryption with " - "key length %ld passed.", tsuite->name, key_lens[i]); + "key length %lu passed.", tsuite->name, key_lens[i]); } /** clean up **/ @@ -214,16 +223,29 @@ goto testcase_cleanup; } + /* Skip tests if pkey = false, but the slot doesn't support CKM_AES_XTS */ + if (is_ep11_token(slot_id) && tsuite->mech.mechanism == CKM_AES_XTS && pkey == FALSE) { + testcase_skip("Slot supports AES-XTS only for protected keys.\n"); + goto testcase_cleanup; + } + /** iterate over key sizes **/ for (i = 0; i < 3; i++) { + if (tsuite->mech.mechanism == CKM_AES_XTS && key_lens[i] == 24) + continue; testcase_begin("%s Multipart Encryption/Decryption with " - "key len=%ld and pkey=%X.", tsuite->name, key_lens[i], pkey); + "key len=%lu and pkey=%X.", tsuite->name, key_lens[i], pkey); + + /** set crypto mech **/ + mech = tsuite->mech; /** generate key **/ - mechkey = aes_keygen; - rc = generate_AESKey(session, key_lens[i], !pkey, - &mechkey, &h_key); + mechkey = mech.mechanism == CKM_AES_XTS ? aes_xts_keygen : aes_keygen; + rc = generate_AESKey(session, + mech.mechanism == CKM_AES_XTS ? key_lens[i] * 2 : + key_lens[i], + !pkey, &mechkey, &h_key); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { testcase_skip("AES key generation is not allowed by policy"); @@ -245,9 +267,6 @@ for (j = 0; j < orig_len; j++) original[j] = j % 255; - /** set crypto mech **/ - mech = tsuite->mech; - /** multipart encryption **/ rc = funcs->C_EncryptInit(session, &mech, h_key); if (rc != CKR_OK) { @@ -255,11 +274,12 @@ goto error; } - /* Encrypt in place except for CBC_PAD, since it + /* Encrypt in place except for CBC_PAD or XTS, since it * pads and pkcs padding can make it unclear about what is * output at what stage. (See pkcs11v2.20 Section 11.2) */ - if (mech.mechanism != CKM_AES_CBC_PAD) { + if (mech.mechanism != CKM_AES_CBC_PAD && + mech.mechanism != CKM_AES_XTS) { memcpy(crypt, original, orig_len); crypt_len = orig_len; @@ -316,11 +336,12 @@ goto error; } - /* decrypt in place. skip for AES_CBC_PAD since it + /* decrypt in place. skip for AES_CBC_PAD or XTS since it * pads and pkcs padding can make it unclear about what is * output at what stage. (See pkcs11v2.20 Section 11.2) */ - if (mech.mechanism != CKM_AES_CBC_PAD) { + if (mech.mechanism != CKM_AES_CBC_PAD && + mech.mechanism != CKM_AES_XTS) { memcpy(decrypt, crypt, crypt_len); k = 0; @@ -373,14 +394,14 @@ if (decrypt_len != orig_len) { testcase_fail("decrypted multipart data length does not" " match original data length.\nexpected " - "length=%ld, but found length=%ld\n", + "length=%lu, but found length=%lu\n", orig_len, decrypt_len); } else if (memcmp(decrypt, original, orig_len)) { testcase_fail("decrypted multipart data does not match" " original data"); } else { testcase_pass("%s Multipart Encryption/Decryption with" - " key length %ld passed.", tsuite->name, key_lens[i]); + " key length %lu passed.", tsuite->name, key_lens[i]); } rc = funcs->C_DestroyObject(session, h_key); @@ -414,6 +435,7 @@ return CKR_HOST_MEMORY; gcm_param->ulIvLen = ulIVLen; memcpy(gcm_param->pIv, pIV, ulIVLen); + gcm_param->ulIvBits = ulIVLen * 8; gcm_param->pAAD = malloc(ulAADLen); if (gcm_param->pAAD == NULL) { @@ -487,16 +509,26 @@ goto testcase_cleanup; } + /* Skip tests if pkey = false, but the slot doesn't support CKM_AES_XTS */ + if (is_ep11_token(slot_id) && tsuite->mech.mechanism == CKM_AES_XTS && pkey == FALSE) { + testcase_skip("Slot supports AES-XTS only for protected keys.\n"); + goto testcase_cleanup; + } + for (i = 0; i < tsuite->tvcount; i++) { - testcase_begin("%s Encryption with published test vector %d and pkey=%X.", + testcase_begin("%s Encryption with published test vector %u and pkey=%X.", tsuite->name, i, pkey); - rc = CKR_OK; + /** get mech **/ + mech = tsuite->mech; /** create key handle **/ rc = create_AESKey(session, !pkey, - tsuite->tv[i].key, tsuite->tv[i].klen, &h_key); + tsuite->tv[i].key, tsuite->tv[i].klen, + mech.mechanism == CKM_AES_XTS ? CKK_AES_XTS : + CKK_AES, + &h_key); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { @@ -508,8 +540,6 @@ goto error; } - /** get mech **/ - mech = tsuite->mech; if (mech.mechanism == CKM_AES_GCM) { gcm_param = ((CK_GCM_PARAMS *) mech.pParameter); gcm_param->ulTagBits = tsuite->tv[i].taglen; @@ -522,6 +552,9 @@ testcase_error("alloc_gcm_param rc=%s", p11_get_ckr(rc)); goto error; } + } else if (mech.mechanism == CKM_AES_XTS) { + mech.pParameter = tsuite->tv[i].iv; + mech.ulParameterLen = tsuite->tv[i].ivlen; } /** clear buffers **/ @@ -573,13 +606,13 @@ if (output_len != expected_len) { testcase_fail("encrypted data length does not match " "test vector's encrypted data length.\n\n" - "expected length=%ld, but found length=%ld\n", + "expected length=%lu, but found length=%lu\n", expected_len, output_len); } else if (memcmp(output, expected, expected_len)) { testcase_fail("encrypted data does not match test " "vector's encrypted data"); } else { - testcase_pass("%s Encryption with test vector %d " + testcase_pass("%s Encryption with test vector %u " "passed.", tsuite->name, i); } @@ -649,16 +682,26 @@ goto testcase_cleanup; } + /* Skip tests if pkey = false, but the slot doesn't support CKM_AES_XTS */ + if (is_ep11_token(slot_id) && tsuite->mech.mechanism == CKM_AES_XTS && pkey == FALSE) { + testcase_skip("Slot supports AES-XTS only for protected keys.\n"); + goto testcase_cleanup; + } + for (i = 0; i < tsuite->tvcount; i++) { testcase_begin("%s Multipart Encryption with published test " - "vector %d and pkey=%X.", tsuite->name, i, pkey); + "vector %u and pkey=%X.", tsuite->name, i, pkey); - rc = CKR_OK; + /** get mech **/ + mech = tsuite->mech; /** create key handle **/ rc = create_AESKey(session, !pkey, - tsuite->tv[i].key, tsuite->tv[i].klen, &h_key); + tsuite->tv[i].key, tsuite->tv[i].klen, + mech.mechanism == CKM_AES_XTS ? CKK_AES_XTS : + CKK_AES, + &h_key); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { @@ -670,8 +713,6 @@ goto error; } - /** get mech **/ - mech = tsuite->mech; if (mech.mechanism == CKM_AES_GCM) { gcm_param = ((CK_GCM_PARAMS *) mech.pParameter); gcm_param->ulTagBits = tsuite->tv[i].taglen; @@ -684,6 +725,9 @@ testcase_error("alloc_gcm_param rc=%s", p11_get_ckr(rc)); goto error; } + } else if (mech.mechanism == CKM_AES_XTS) { + mech.pParameter = tsuite->tv[i].iv; + mech.ulParameterLen = tsuite->tv[i].ivlen; } /** clear buffers **/ @@ -776,14 +820,14 @@ if (crypt_len != expected_len) { testcase_fail("encrypted multipart data length does " "not match test vector's encrypted data length." - "\n\nexpected length=%ld, but found length=%ld" + "\n\nexpected length=%lu, but found length=%lu" "\n", expected_len, crypt_len); } else if (memcmp(crypt, expected, expected_len)) { testcase_fail("encrypted multipart data does not match" " test vector's encrypted data.\n"); } else { testcase_pass("%s Multipart Encryption with test " - "vector %d passed.", tsuite->name, i); + "vector %u passed.", tsuite->name, i); } rc = funcs->C_DestroyObject(session, h_key); @@ -852,16 +896,26 @@ goto testcase_cleanup; } + /* Skip tests if pkey = false, but the slot doesn't support CKM_AES_XTS */ + if (is_ep11_token(slot_id) && tsuite->mech.mechanism == CKM_AES_XTS && pkey == FALSE) { + testcase_skip("Slot supports AES-XTS only for protected keys.\n"); + goto testcase_cleanup; + } + for (i = 0; i < tsuite->tvcount; i++) { - testcase_begin("%s Decryption with published test vector %d and pkey=%X.", + testcase_begin("%s Decryption with published test vector %u and pkey=%X.", tsuite->name, i, pkey); - rc = CKR_OK; + /** get mech **/ + mech = tsuite->mech; /** create key handle **/ rc = create_AESKey(session, !pkey, - tsuite->tv[i].key, tsuite->tv[i].klen, &h_key); + tsuite->tv[i].key, tsuite->tv[i].klen, + mech.mechanism == CKM_AES_XTS ? CKK_AES_XTS : + CKK_AES, + &h_key); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { @@ -872,10 +926,8 @@ testcase_error("C_CreateObject rc=%s", p11_get_ckr(rc)); goto error; } - - /** get mech **/ - mech = tsuite->mech; - if (mech.mechanism == CKM_AES_GCM) { + + if (mech.mechanism == CKM_AES_GCM) { gcm_param = ((CK_GCM_PARAMS *) mech.pParameter); gcm_param->ulTagBits = tsuite->tv[i].taglen; rc = alloc_gcm_param(gcm_param, @@ -887,6 +939,9 @@ testcase_error("alloc_gcm_param rc=%s", p11_get_ckr(rc)); goto error; } + } else if (mech.mechanism == CKM_AES_XTS) { + mech.pParameter = tsuite->tv[i].iv; + mech.ulParameterLen = tsuite->tv[i].ivlen; } /** clear buffers **/ @@ -937,13 +992,13 @@ if (output_len != expected_len) { testcase_fail("decrypted data length does not match " "test vector's decrypted data length.\n\n" - "expected length=%ld, but found length=%ld\n", + "expected length=%lu, but found length=%lu\n", expected_len, output_len); } else if (memcmp(output, expected, expected_len)) { testcase_fail("decrypted data does not match test " "vector's decrypted data"); } else { - testcase_pass("%s Decryption with test vector %d " + testcase_pass("%s Decryption with test vector %u " "passed.", tsuite->name, i); } @@ -1013,14 +1068,26 @@ goto testcase_cleanup; } + /* Skip tests if pkey = false, but the slot doesn't support CKM_AES_XTS */ + if (is_ep11_token(slot_id) && tsuite->mech.mechanism == CKM_AES_XTS && pkey == FALSE) { + testcase_skip("Slot supports AES-XTS only for protected keys.\n"); + goto testcase_cleanup; + } + for (i = 0; i < tsuite->tvcount; i++) { testcase_begin("%s Multipart Decryption with published test " - "vector %d and pkey=%X.", tsuite->name, i, pkey); + "vector %u and pkey=%X.", tsuite->name, i, pkey); + + /** get mech **/ + mech = tsuite->mech; /** create key handle **/ rc = create_AESKey(session, !pkey, - tsuite->tv[i].key, tsuite->tv[i].klen, &h_key); + tsuite->tv[i].key, tsuite->tv[i].klen, + mech.mechanism == CKM_AES_XTS ? CKK_AES_XTS : + CKK_AES, + &h_key); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { @@ -1046,6 +1113,9 @@ testcase_error("alloc_gcm_param rc=%s", p11_get_ckr(rc)); goto error; } + } else if (mech.mechanism == CKM_AES_XTS) { + mech.pParameter = tsuite->tv[i].iv; + mech.ulParameterLen = tsuite->tv[i].ivlen; } /** clear buffers **/ @@ -1136,14 +1206,14 @@ if (p_len != expected_len) { testcase_fail("decrypted multipart data length does " "not match test vector's decrypted data " - "length.\n\nexpected length=%ld, but found " - "length=%ld\n", expected_len, p_len); + "length.\n\nexpected length=%lu, but found " + "length=%lu\n", expected_len, p_len); } else if (memcmp(plaintext, expected, expected_len)) { testcase_fail("decrypted multipart data does not match" " test vector's decrypted data.\n"); } else { testcase_pass("%s Multipart Decryption with test " - "vector %d passed.", tsuite->name, i); + "vector %u passed.", tsuite->name, i); } rc = funcs->C_DestroyObject(session, h_key); @@ -1195,7 +1265,7 @@ CK_RV rc = CKR_OK; CK_SLOT_ID slot_id = SLOT_ID; CK_OBJECT_CLASS key_class = CKO_SECRET_KEY; - CK_KEY_TYPE key_type = CKK_AES; + CK_KEY_TYPE key_type; CK_ATTRIBUTE template[] = { {CKA_CLASS, &key_class, sizeof(key_class)}, {CKA_KEY_TYPE, &key_type, sizeof(key_type)}, @@ -1231,6 +1301,12 @@ goto testcase_cleanup; } + /* Skip tests if pkey = false, but the slot doesn't support CKM_AES_XTS */ + if (is_ep11_token(slot_id) && tsuite->mech.mechanism == CKM_AES_XTS && pkey == FALSE) { + testcase_skip("Slot supports AES-XTS only for protected keys.\n"); + goto testcase_cleanup; + } + /* key sizes must be a multiple of AES block size in order to be passed in as data. Recall AES expects data in multiple of AES block size. */ @@ -1239,12 +1315,16 @@ if (key_lens[i] % AES_BLOCK_SIZE != 0) continue; - testcase_begin("%s Wrap/Unwrap key test with keylength=%ld and pkey=%X.", + if (tsuite->mech.mechanism == CKM_AES_XTS && key_lens[i] == 24) + continue; + + testcase_begin("%s Wrap/Unwrap key test with keylength=%lu and pkey=%X.", tsuite->name, key_lens[i], pkey); /** set mechanisms **/ mech = tsuite->mech; - mechkey = aes_keygen; + mechkey = mech.mechanism == CKM_AES_XTS ? aes_xts_keygen : aes_keygen; + key_type = mech.mechanism == CKM_AES_XTS ? CKK_AES_XTS : CKK_AES; /** set key_size **/ key_size = key_lens[i]; @@ -1255,7 +1335,10 @@ memset(decrypt, 0, sizeof(decrypt)); /** generate crypto key (must be extractable) **/ - rc = generate_AESKey(session, key_lens[i], CK_TRUE, &mechkey, &h_key); + rc = generate_AESKey(session, + mech.mechanism == CKM_AES_XTS ? key_lens[i] * 2 : + key_lens[i], + CK_TRUE, &mechkey, &h_key); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { testcase_skip("AES key generation is not allowed by policy"); @@ -1267,7 +1350,9 @@ } /** generate wrapping key **/ - rc = generate_AESKey(session, key_lens[i], !pkey, + rc = generate_AESKey(session, + mech.mechanism == CKM_AES_XTS ? key_lens[i] * 2 : + key_lens[i], !pkey, &mechkey, &w_key); if (rc != CKR_OK) { testcase_error("C_GenerateKey rc=%s", p11_get_ckr(rc)); @@ -1455,6 +1540,8 @@ CK_OBJECT_CLASS keyclass = CKO_PRIVATE_KEY; CK_KEY_TYPE keytype = CKK_RSA; CK_SLOT_ID slot_id = SLOT_ID; + CK_BBOOL extractable = !pkey; + CK_BBOOL pkeyextractable = pkey; CK_ATTRIBUTE pub_tmpl[] = { {CKA_MODULUS_BITS, &bits, sizeof(bits)}, @@ -1467,7 +1554,9 @@ {CKA_KEY_TYPE, &keytype, sizeof(keytype)}, }; CK_ATTRIBUTE key_gen_tmpl[] = { + {CKA_EXTRACTABLE, &extractable, sizeof(CK_BBOOL)}, {CKA_VALUE_LEN, &key_size, sizeof(CK_ULONG)}, + {CKA_IBM_PROTKEY_EXTRACTABLE, &pkeyextractable, sizeof(CK_BBOOL)}, }; CK_ULONG key_gen_tmpl_len = sizeof(key_gen_tmpl) / sizeof(CK_ATTRIBUTE); @@ -1517,6 +1606,14 @@ goto testcase_cleanup; } + if (!wrap_supported(slot_id, tsuite->mech)) { + testsuite_skip(3, "Slot %u doesn't support wrapping with %s (0x%x)", + (unsigned int) slot_id, + mech_to_str(tsuite->mech.mechanism), + (unsigned int) tsuite->mech.mechanism); + goto testcase_cleanup; + } + rc = funcs->C_GetMechanismInfo(slot_id, CKM_RSA_PKCS_KEY_PAIR_GEN, &mech_info); if (rc != CKR_OK) { testcase_error("C_GetMechanismInfo rc=%s", p11_get_ckr(rc)); @@ -1527,14 +1624,18 @@ bits = mech_info.ulMinKeySize; for (i = 0; i < 3; i++) { + if (tsuite->mech.mechanism == CKM_AES_XTS && key_lens[i] == 24) + continue; - testcase_begin("%s wrap/unwrap of RSA key for key length=%ld and pkey=%X.", + testcase_begin("%s wrap/unwrap of RSA key for key length=%lu and pkey=%X.", tsuite->name, key_lens[i], pkey); - key_size = key_lens[i]; + key_size = tsuite->mech.mechanism == CKM_AES_XTS ? + key_lens[i] * 2 : key_lens[i]; /** first mechanism generate AES wrapping key **/ - mech.mechanism = CKM_AES_KEY_GEN; + mech.mechanism = tsuite->mech.mechanism == CKM_AES_XTS ? + CKM_AES_XTS_KEY_GEN : CKM_AES_KEY_GEN; mech.ulParameterLen = 0; mech.pParameter = NULL; @@ -1663,7 +1764,7 @@ testcase_new_assertion(); if (orig_len != decipher_len) { testcase_fail("lengths don't match: " - "%ld vs %ld\n", orig_len, decipher_len); + "%lu vs %lu\n", orig_len, decipher_len); rc = CKR_GENERAL_ERROR; } else if (memcmp(original, decipher, orig_len)) { testcase_fail("deciphered data does not match" @@ -1778,7 +1879,7 @@ for (i = 0; i < 3; i++) { - testcase_begin("%s wrap/unwrap of RSA key for key length=%ld and pkey=%X.", + testcase_begin("%s wrap/unwrap of RSA key for key length=%lu and pkey=%X.", tsuite->name, key_lens[i], pkey); key_size = key_lens[i]; @@ -1972,7 +2073,7 @@ for (i = 0; i < 3; i++) { - testcase_begin("%s wrap/unwrap of RSA key for key length=%ld and pkey=%X.", + testcase_begin("%s wrap/unwrap of RSA key for key length=%lu and pkey=%X.", tsuite->name, key_lens[i], pkey); key_size = key_lens[i]; @@ -2121,12 +2222,13 @@ for (i = 0; i < tsuite->tvcount; i++) { - testcase_begin("%s Sign/Verify MAC with published test vector %d and pkey=%X.", + testcase_begin("%s Sign/Verify MAC with published test vector %u and pkey=%X.", tsuite->name, i, pkey); /** create key handle **/ rc = create_AESKey(session, !pkey, - tsuite->tv[i].key, tsuite->tv[i].klen, &h_key); + tsuite->tv[i].key, tsuite->tv[i].klen, CKK_AES, + &h_key); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { @@ -2244,20 +2346,20 @@ mech.mechanism == CKM_AES_MAC_GENERAL) && actual_len != tsuite->tv[i].tlen) { testcase_fail("signature length does not match test vector's " - "signature length\nexpected length=%d, found " - "length=%ld", tsuite->tv[i].tlen, actual_len); + "signature length\nexpected length=%u, found " + "length=%lu", tsuite->tv[i].tlen, actual_len); } else if (mech.mechanism != CKM_AES_CMAC_GENERAL && mech.mechanism != CKM_AES_MAC_GENERAL && actual_len != mac_len) { testcase_fail("signature length does not match test vector's " - "signature length\nexpected length=%ld, found " - "length=%ld", mac_len, actual_len); + "signature length\nexpected length=%lu, found " + "length=%lu", mac_len, actual_len); } else if (memcmp(actual, tsuite->tv[i].mac, tsuite->tv[i].tlen < mac_len ? tsuite->tv[i].tlen : mac_len)) { testcase_fail("signature does not match test vector's signature"); } else { - testcase_pass("%s Sign/Verify MAC with test vector %d " + testcase_pass("%s Sign/Verify MAC with test vector %u " "passed.", tsuite->name, i); } @@ -2280,7 +2382,7 @@ return rc; } -CK_RV do_SetAttributeValuesPkey() +CK_RV do_SetAttributeValuesPkey(void) { CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; CK_FLAGS flags; @@ -2375,7 +2477,7 @@ return rc; } -CK_RV do_EncryptDecryptAESPkey() +CK_RV do_EncryptDecryptAESPkey(void) { CK_ULONG keylen = 16; CK_BBOOL btrue = CK_TRUE; @@ -2490,7 +2592,7 @@ testcase_fail("Didn't find key with label '%s'in repository", label); goto testcase_cleanup; } else if (count > 1) { - testcase_skip("Found %ld objs with label '%s', only expected one. " + testcase_skip("Found %lu objs with label '%s', only expected one. " "Skipping this test.\n", count, label); rc = funcs->C_FindObjectsFinal(session); goto testcase_cleanup; @@ -2580,7 +2682,7 @@ /** * Special tests for protected key support. */ -CK_RV aes_funcs_pkey() +CK_RV aes_funcs_pkey(void) { CK_RV rv; @@ -2591,7 +2693,7 @@ return rv; } -CK_RV aes_funcs() +CK_RV aes_funcs(void) { unsigned int i; CK_RV rv = CKR_OK; @@ -2697,9 +2799,11 @@ pkey = CK_FALSE; rv = aes_funcs(); - pkey = CK_TRUE; - rv += aes_funcs(); - rv += aes_funcs_pkey(); + if (is_ep11_token(SLOT_ID)) { + pkey = CK_TRUE; + rv += aes_funcs(); + rv += aes_funcs_pkey(); + } testcase_print_result(); diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/aes.h opencryptoki-3.20.0+dfsg/testcases/crypto/aes.h --- opencryptoki-3.18.0+dfsg/testcases/crypto/aes.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/aes.h 2023-02-13 09:22:42.000000000 +0100 @@ -85,6 +85,7 @@ struct CK_GCM_PARAMS aesgcm = { .ulIvLen = AES_BLOCK_SIZE, + .ulIvBits = AES_BLOCK_SIZE * 8, .ulAADLen = 0, .ulTagBits = 16, }; @@ -95,6 +96,12 @@ .pParameter = NULL, }; +struct CK_MECHANISM aes_xts_keygen = { + .mechanism = CKM_AES_XTS_KEY_GEN, + .ulParameterLen = 0, + .pParameter = NULL, +}; + struct mac_test_vector { unsigned char key[MAX_KEY_SIZE]; unsigned char klen; @@ -935,6 +942,122 @@ } }; +static struct aes_test_vector aes_xts_tv[] = { + { // #0 + .key = {0x46, 0xe6, 0xed, 0x9e, 0xf4, 0x2d, 0xcd, 0xb3, + 0xc8, 0x93, 0x09, 0x3c, 0x28, 0xe1, 0xfc, 0x0f, + 0x91, 0xf5, 0xca, 0xa3, 0xb6, 0xe0, 0xbc, 0x5a, + 0x14, 0xe7, 0x83, 0x21, 0x5c, 0x1d, 0x5b, 0x61,}, + .klen = 32, + .plaintext = {0xe3, 0x77, 0x8d, 0x68, 0xe7, 0x30, 0xef, 0x94, + 0x5b, 0x4a, 0xe3, 0xbc, 0x5b, 0x93, 0x6b, 0xdd,}, + .plen = 16, + .ciphertext = {0x97, 0x40, 0x9f, 0x1f, 0x71, 0xae, 0x45, 0x21, + 0xcb, 0x49, 0xa3, 0x29, 0x73, 0xde, 0x4d, 0x05,}, + .clen = 16, + .iv = {0x72, 0xf3, 0xb0, 0x54, 0xcb, 0xdc, 0x2f, 0x9e, + 0x3c, 0x5b, 0xc5, 0x51, 0xd4, 0x4d, 0xdb, 0xa0}, + .ivlen = 16, + .num_chunks_ciph = 3, + .chunks_ciph = {10, 0, 6}, + }, { // #1 + .key = {0x93, 0x56, 0xcd, 0xad, 0x25, 0x1a, 0xb6, 0x11, + 0x14, 0xce, 0xc2, 0xc4, 0x4a, 0x60, 0x92, 0xdd, + 0xe9, 0xf7, 0x46, 0xcc, 0x65, 0xae, 0x3b, 0xd4, + 0x96, 0x68, 0x64, 0xaa, 0x36, 0x26, 0xd1, 0x88,}, + .klen = 32, + .plaintext = {0xce, 0x17, 0x6b, 0xdd, 0xe3, 0x39, 0x50, 0x5b, + 0xa1, 0x5d, 0xea, 0x36, 0xd2, 0x8c, 0xe8, 0x7d,}, + .plen = 16, + .ciphertext = {0x22, 0xf5, 0xf9, 0x37, 0xdf, 0xb3, 0x9e, 0x5b, + 0x74, 0x25, 0xed, 0x86, 0x3d, 0x31, 0x0b, 0xe1,}, + .clen = 16, + .iv = {0x68, 0x88, 0x27, 0x83, 0x65, 0x24, 0x36, 0xc4, + 0x85, 0x7a, 0x88, 0xc0, 0xc3, 0x73, 0x41, 0x7e,}, + .ivlen = 16, + .num_chunks_ciph = 3, + .chunks_ciph = {10, -1, 6}, + }, + { // #2 + .key = {0x97, 0x09, 0x8b, 0x46, 0x5a, 0x44, 0xca, 0x75, + 0xe7, 0xa1, 0xc2, 0xdb, 0xfc, 0x40, 0xb7, 0xa6, + 0x1a, 0x20, 0xe3, 0x2c, 0x6d, 0x9d, 0xbf, 0xda, + 0x80, 0x72, 0x6f, 0xee, 0x10, 0x54, 0x1b, 0xab, + 0x47, 0x54, 0x63, 0xca, 0x07, 0xc1, 0xc1, 0xe4, + 0x49, 0x61, 0x73, 0x32, 0x14, 0x68, 0xd1, 0xab, + 0x3f, 0xad, 0x8a, 0xd9, 0x1f, 0xcd, 0xc6, 0x2a, + 0xbe, 0x07, 0xbf, 0xf8, 0xef, 0x96, 0x1b, 0x6b,}, + .klen = 64, + .plaintext = {0xd1, 0x9c, 0xfb, 0x38, 0x3b, 0xaf, 0x87, 0x2e, + 0x6f, 0x12, 0x16, 0x87, 0x45, 0x1d, 0xe1, 0x5c,}, + .plen = 16, + .ciphertext = {0xeb, 0x22, 0x26, 0x9b, 0x14, 0x90, 0x50, 0x27, + 0xdc, 0x73, 0xc4, 0xa4, 0x0f, 0x93, 0x80, 0x69,}, + .clen = 16, + .iv = {0x15, 0x60, 0x1e, 0x2e, 0x35, 0x85, 0x10, 0xa0, + 0x9d, 0xdc, 0xa4, 0xea, 0x17, 0x51, 0xf4, 0x3c,}, + .ivlen = 16, + .num_chunks_ciph = 4, + .chunks_ciph = {4, 4, 4, 4}, + }, + { // #3 + .key = {0xfb, 0xf0, 0x77, 0x6e, 0x7d, 0xbe, 0x49, 0x10, + 0xfb, 0x0c, 0x12, 0x0f, 0x41, 0x85, 0x71, 0x21, + 0x92, 0x6c, 0x05, 0x2f, 0xd6, 0x5a, 0x27, 0x8c, + 0xd2, 0xf0, 0xd9, 0x8d, 0xa5, 0x4e, 0xdf, 0xd5, + 0x08, 0x03, 0xa4, 0x2f, 0xbe, 0x6f, 0xd1, 0x33, + 0x58, 0x49, 0x00, 0xe8, 0xdc, 0x7a, 0x11, 0x52, + 0x39, 0x1f, 0x82, 0x2d, 0x76, 0xa7, 0x56, 0x68, + 0xcf, 0xce, 0x7f, 0x8d, 0xde, 0x20, 0x3e, 0xc8,}, + .klen = 64, + .plaintext = {0x3e, 0x2e, 0x26, 0x9d, 0x78, 0x3a, 0x2b, 0x29, + 0xe8, 0x73, 0xd6, 0x73, 0x47, 0x9f, 0x51, 0x16, + 0x73, 0x4f, 0xe0, 0x3e, 0xe3, 0x29, 0x65, 0xed, + 0xc4, 0x79, 0x35, 0xc0, 0xea, 0x99, 0xa0, 0x64, + 0xbd, 0x44, 0x4b, 0xec, 0x12, 0x5b, 0x2c, 0x78, + 0x9d, 0xb9, 0xde, 0x6d, 0x18, 0x35, 0x92, 0x05, + 0x3b, 0x48, 0xa8, 0x77, 0xa9, 0x5a, 0xc2, 0x55, + 0x9c, 0x3d, 0xdf, 0xc7, 0xb4, 0xdb, 0x99, 0x07,}, + .plen = 64, + .ciphertext = {0x4c, 0x70, 0xbd, 0xbb, 0x77, 0x30, 0x2b, 0x7f, + 0x1f, 0xdd, 0xca, 0x50, 0xdc, 0x70, 0x73, 0x1e, + 0x00, 0x8a, 0x26, 0x55, 0xd2, 0x2a, 0xd0, 0x20, + 0x0c, 0x11, 0x1f, 0xd3, 0x2a, 0x67, 0x5a, 0x7e, + 0x09, 0x97, 0x11, 0x43, 0x6f, 0x98, 0xd2, 0x1c, + 0x72, 0x77, 0x2e, 0x0d, 0xd7, 0x67, 0x2f, 0xf5, + 0xfd, 0x00, 0xdd, 0xcb, 0xe1, 0x1e, 0xb9, 0x7e, + 0x69, 0x87, 0x83, 0xbf, 0xa4, 0x05, 0x46, 0xe3,}, + .clen = 64, + .iv = {0x39, 0x5b, 0x6a, 0xcf, 0x9a, 0xdc, 0xd2, 0x91, + 0xc2, 0xc9, 0x48, 0x86, 0x36, 0x33, 0xaf, 0xf8,}, + .ivlen = 16, + .num_chunks_ciph = 6, + .chunks_ciph = {15, 0, 18, -1, 10, 21}, + }, { // #4 + .key = {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11, + 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, + 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23, + 0x24, 0x25, 0x26, 0x27, 0x28, 0x29, 0x2a, 0x2b, 0x2c, + 0x2d, 0x2e, 0x2f, 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, + 0x36, 0x37, 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, + 0x3f + }, + .klen = 64, + .iv = {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f}, + .ivlen = 16, + .plaintext = {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, + 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10}, + .plen = 17, + .ciphertext = {0x02, 0x04, 0x4b, 0x67, 0x14, 0x6e, 0x6a, 0x91, 0xbf, + 0x0c, 0xc1, 0xfe, 0xe7, 0xcd, 0x88, 0x12, 0xb8}, + .clen = 17, + .num_chunks_ciph = 3, + .chunks_ciph = { 5, 5, 7}, + } +}; + /** * NIST Special Publication 800-38B * https://csrc.nist.gov/Projects/Cryptographic-Algorithm-Validation-Program/ @@ -2038,7 +2161,7 @@ } }; -#define NUM_OF_PUBLISHED_TESTSUITES 7 +#define NUM_OF_PUBLISHED_TESTSUITES 8 struct published_test_suite_info published_test_suites[] = { { @@ -2083,10 +2206,16 @@ .tv = aes_ofb_tv, .size = AES_BLOCK_SIZE, .mech = {CKM_AES_OFB, &aes_iv, AES_IV_SIZE}, + }, { + .name = "AES_XTS", + .tvcount = 5, + .tv = aes_xts_tv, + .size = AES_BLOCK_SIZE, + .mech = {CKM_AES_XTS, &aes_iv, AES_IV_SIZE}, } }; -#define NUM_OF_GENERATED_TESTSUITES 4 +#define NUM_OF_GENERATED_TESTSUITES 5 struct generated_test_suite_info generated_test_suites[] = { { @@ -2101,6 +2230,9 @@ }, { .name = "AES_CTR", .mech = {CKM_AES_CTR, &aesctr, sizeof(aesctr)}, + }, { + .name = "AES_XTS", + .mech = {CKM_AES_XTS, &aes_iv, AES_IV_SIZE}, } }; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/crypto.mk opencryptoki-3.20.0+dfsg/testcases/crypto/crypto.mk --- opencryptoki-3.18.0+dfsg/testcases/crypto/crypto.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/crypto.mk 2023-02-13 09:22:42.000000000 +0100 @@ -4,11 +4,13 @@ testcases/crypto/rsa_tests testcases/crypto/dh_tests \ testcases/crypto/ssl3_tests testcases/crypto/ec_tests \ testcases/crypto/rsaupdate_tests \ - testcases/crypto/dilithium_tests testcases/crypto/ab_tests + testcases/crypto/dilithium_tests testcases/crypto/ab_tests \ + testcases/crypto/kyber_tests noinst_HEADERS += \ testcases/crypto/aes.h testcases/crypto/des.h \ testcases/crypto/des3.h testcases/crypto/digest.h \ - testcases/crypto/ec.h testcases/crypto/rsa.h + testcases/crypto/ec.h testcases/crypto/rsa.h \ + testcases/crypto/dilithium.h testcases/crypto/kyber.h testcases_crypto_aes_tests_CFLAGS = ${testcases_inc} testcases_crypto_aes_tests_LDADD = testcases/common/libcommon.la @@ -58,3 +60,7 @@ testcases_crypto_ab_tests_CFLAGS = ${testcases_inc} testcases_crypto_ab_tests_LDADD = testcases/common/libcommon.la testcases_crypto_ab_tests_SOURCES = testcases/crypto/abfunc.c + +testcases_crypto_kyber_tests_CFLAGS = ${testcases_inc} +testcases_crypto_kyber_tests_LDADD = testcases/common/libcommon.la +testcases_crypto_kyber_tests_SOURCES = testcases/crypto/kyber_func.c diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/des3_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/des3_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/des3_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/des3_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -56,7 +56,7 @@ /** iterate over test vectors **/ for (i = 0; i < tsuite->tvcount; i++) { - testcase_begin("%s Encryption with test vector %d", tsuite->name, i); + testcase_begin("%s Encryption with test vector %u", tsuite->name, i); rc = CKR_OK; // set rc @@ -111,14 +111,14 @@ if (actual_len != expected_len) { testcase_fail("encrypted data length does not match " "test vector's encrypted data length.\n" - "expected length=%ld, but found length=" "%ld\n", + "expected length=%lu, but found length=" "%lu\n", expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { testcase_fail("encrypted data does not match test " "vector's encrypted data.\n"); } else { testcase_pass("%s Encryption with test vector " - "%d passed.", tsuite->name, i); + "%u passed.", tsuite->name, i); } /** clean up **/ @@ -182,7 +182,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin testcase **/ - testcase_begin("%s Multipart Encryption with test vector %d.", + testcase_begin("%s Multipart Encryption with test vector %u.", tsuite->name, i); rc = CKR_OK; // set rc @@ -285,14 +285,14 @@ if (crypt_len != expected_len) { testcase_fail("multipart encrypted data length does " "not match test vector's encrypted data length.\n" - "expected length=%ld, but found length=%ld\n", + "expected length=%lu, but found length=%lu\n", expected_len, crypt_len); } else if (memcmp(crypt, expected, expected_len)) { testcase_fail("multipart encrypted data does " "not match test vector's encrypted data.\n"); } else { testcase_pass("%s Multipart Encryption with test vector" - " %d passed.", tsuite->name, i); + " %u passed.", tsuite->name, i); } rc = funcs->C_DestroyObject(session, h_key); @@ -356,7 +356,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("%s Decryption with test vector %d.", tsuite->name, i); + testcase_begin("%s Decryption with test vector %u.", tsuite->name, i); rc = CKR_OK; // set rc @@ -410,13 +410,13 @@ if (actual_len != expected_len) { testcase_fail("decrypted data length does not match test " "vector's decrypted data length.\nexpected length=" - "%ld, but found length=%ld\n", + "%lu, but found length=%lu\n", expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { testcase_fail("decrypted data does not match test " "vector's decrypted data.\n"); } else { - testcase_pass("%s Decryption with test vector %d " + testcase_pass("%s Decryption with test vector %u " "passed.", tsuite->name, i); } @@ -482,7 +482,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("%s Decryption with test vector %d.", tsuite->name, i); + testcase_begin("%s Decryption with test vector %u.", tsuite->name, i); rc = CKR_OK; // set rc @@ -584,14 +584,14 @@ if (p_len != expected_len) { testcase_fail("decrypted multipart data length does " "not match test vector's decrypted data " - "length.\nexpected length=%ld, but " - "found length=%ld\n", expected_len, p_len); + "length.\nexpected length=%lu, but " + "found length=%lu\n", expected_len, p_len); } else if (memcmp(plaintext, expected, expected_len)) { testcase_fail("decrypted multipart data does not " "match test vector's decrypted data.\n"); } else { testcase_pass("%s Multipart Decryption with test " - "vector %d passed.", tsuite->name, i); + "vector %u passed.", tsuite->name, i); } /** clean up **/ @@ -710,7 +710,7 @@ if (decrypt_len != original_len) { testcase_fail("decrypted data length does not match original data " - "length.\nexpected length=%ld, but found length=%ld\n", + "length.\nexpected length=%lu, but found length=%lu\n", original_len, decrypt_len); } else if (memcmp(decrypt, original, original_len)) { testcase_fail("decrypted data does not match original data"); @@ -921,8 +921,8 @@ if (decrypt_len != original_len) { testcase_fail("decrypted multipart data length does not match " - "original data length.\nexpected length=%ld, but " - "found length=%ld\n", original_len, decrypt_len); + "original data length.\nexpected length=%lu, but " + "found length=%lu\n", original_len, decrypt_len); } else if (memcmp(decrypt, original, original_len)) { testcase_fail("decrypted multipart data does not match " "original data"); @@ -1104,7 +1104,7 @@ if (actual_len != expected_len) { testcase_fail("decrypted data length does not match original data " - "length.\nexpected length=%ld, but found length=%ld\n", + "length.\nexpected length=%lu, but found length=%lu\n", expected_len, actual_len); } else if (memcmp(actual, expected, actual_len)) { testcase_fail("decrypted data does not match original data."); @@ -1136,7 +1136,7 @@ int k; CK_SESSION_HANDLE session; CK_MECHANISM mech; - CK_OBJECT_HANDLE h_key; + CK_OBJECT_HANDLE h_key = CK_INVALID_HANDLE; CK_FLAGS flags; CK_RV rc = CKR_OK; CK_SLOT_ID slot_id = SLOT_ID; @@ -1169,7 +1169,7 @@ } for (i = 0; i < tsuite->tvcount; i++) { - testcase_begin("%s Sign/Verify MAC with published test vector %d.", + testcase_begin("%s Sign/Verify MAC with published test vector %u.", tsuite->name, i); /** create key handle **/ @@ -1291,20 +1291,20 @@ mech.mechanism == CKM_DES3_MAC_GENERAL) && actual_len != tsuite->tv[i].tlen) { testcase_fail("signature length does not match test vector's " - "signature length\nexpected length=%d, found " - "length=%ld", tsuite->tv[i].tlen, actual_len); + "signature length\nexpected length=%u, found " + "length=%lu", tsuite->tv[i].tlen, actual_len); } else if (mech.mechanism != CKM_DES3_CMAC_GENERAL && mech.mechanism != CKM_DES3_MAC_GENERAL && actual_len != mac_len) { testcase_fail("signature length does not match test vector's " - "signature length\nexpected length=%ld, found " - "length=%ld", mac_len, actual_len); + "signature length\nexpected length=%lu, found " + "length=%lu", mac_len, actual_len); } else if (memcmp(actual, tsuite->tv[i].mac, tsuite->tv[i].tlen < mac_len ? tsuite->tv[i].tlen : mac_len)) { testcase_fail("signature does not match test vector's signature"); } else { - testcase_pass("%s Sign/Verify MAC with test vector %d " + testcase_pass("%s Sign/Verify MAC with test vector %u " "passed.", tsuite->name, i); } @@ -1317,7 +1317,8 @@ goto testcase_cleanup; error: - rc = funcs->C_DestroyObject(session, h_key); + if (h_key != CK_INVALID_HANDLE) + rc = funcs->C_DestroyObject(session, h_key); if (rc != CKR_OK) testcase_error("C_DestroyObject rc=%s", p11_get_ckr(rc)); @@ -1327,7 +1328,7 @@ return rc; } -CK_RV des3_funcs() +CK_RV des3_funcs(void) { int i; CK_RV rv; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/des_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/des_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/des_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/des_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -57,7 +57,7 @@ /** begin testcase **/ testcase_begin("%s Encryption with published test vector " - "%d.", tsuite->name, i); + "%u.", tsuite->name, i); rc = CKR_OK; // set rc @@ -111,13 +111,13 @@ if (actual_len != expected_len) { testcase_fail("encrypted data length does not " "match test vector's encrypted data " - "length.\n\nexpected length=%ld, but found" - " length=%ld\n", expected_len, actual_len); + "length.\n\nexpected length=%lu, but found" + " length=%lu\n", expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { testcase_fail("encrypted data does not match test " "vector's encrypted data"); } else { - testcase_pass("%s Encryption with test vector %d " + testcase_pass("%s Encryption with test vector %u " "passed.", tsuite->name, i); } @@ -183,7 +183,7 @@ /** begin test **/ testcase_begin("%s Multipart Encryption with published " - "test vector %d.", tsuite->name, i); + "test vector %u.", tsuite->name, i); rc = CKR_OK; // set rc @@ -286,14 +286,14 @@ if (crypt_len != expected_len) { testcase_fail("encrypted multipart data length " "does not match test vector's encrypted " - "data length.\n\nexpected length=%ld, " - "but found length=%ld\n", expected_len, crypt_len); + "data length.\n\nexpected length=%lu, " + "but found length=%lu\n", expected_len, crypt_len); } else if (memcmp(crypt, expected, expected_len)) { testcase_fail("encrypted multipart data does not " "match test vector's encrypted data.\n"); } else { testcase_pass("%s Multipart Encryption with test " - "vector %d passed.", tsuite->name, i); + "vector %u passed.", tsuite->name, i); } rc = funcs->C_DestroyObject(session, h_key); @@ -357,7 +357,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("%s Decryption with published test vector " "%d.", + testcase_begin("%s Decryption with published test vector %u.", tsuite->name, i); rc = CKR_OK; @@ -412,13 +412,13 @@ if (actual_len != expected_len) { testcase_fail("decrypted data length does not " "match test vector's decrypted data " - "length.\n\nexpected length=%ld, but found" - " length=%ld\n", expected_len, actual_len); + "length.\n\nexpected length=%lu, but found" + " length=%lu\n", expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { testcase_fail("decrypted data does not match test " "vector's decrypted data.\n"); } else { - testcase_pass("%s Decryption with test vector %d " + testcase_pass("%s Decryption with test vector %u " "passed.", tsuite->name, i); } @@ -486,7 +486,7 @@ /** begin test **/ testcase_begin("%s Multipart Decryption with published " - "test vector %d.", tsuite->name, i); + "test vector %u.", tsuite->name, i); rc = CKR_OK; // set rc @@ -587,14 +587,14 @@ if (p_len != expected_len) { testcase_fail("decrypted multipart data length " "does not match test vector's decrypted " - "data length.\n\nexpected length=%ld, but " - "found length=%ld\n", expected_len, p_len); + "data length.\n\nexpected length=%lu, but " + "found length=%lu\n", expected_len, p_len); } else if (memcmp(plaintext, expected, expected_len)) { testcase_fail("decrypted multipart data does not " "match test vector's decrypted data.\n"); } else { testcase_pass("%s Multipart Decryption with test " - "vector %d passed.", tsuite->name, i); + "vector %u passed.", tsuite->name, i); } /** clean up **/ @@ -714,8 +714,8 @@ if (decrypt_len != original_len) { testcase_fail("decrypted data length does not match " - "original data length.\nexpected length=%ld, " - "but found length=%ld\n", original_len, decrypt_len); + "original data length.\nexpected length=%lu, " + "but found length=%lu\n", original_len, decrypt_len); } else if (memcmp(decrypt, original, original_len)) { testcase_fail("decrypted data does not match original " "data"); } else { @@ -882,8 +882,8 @@ if (decrypt_len != original_len) { testcase_fail("decrypted multipart data length does not " - "match original data length.\nexpected length=%ld," - " but found length=%ld\n", original_len, decrypt_len); + "match original data length.\nexpected length=%lu," + " but found length=%lu\n", original_len, decrypt_len); } else if (memcmp(decrypt, original, original_len)) { testcase_fail("decrypted data does not match original " "data"); } else { @@ -1047,7 +1047,7 @@ testcase_new_assertion(); if (actual_len != expected_len) { - testcase_fail("expected length=%ld, but found length=%ld" + testcase_fail("expected length=%lu, but found length=%lu" "\n", expected_len, actual_len); rc = CKR_GENERAL_ERROR; } else if (memcmp(actual, expected, actual_len)) { @@ -1079,7 +1079,7 @@ return rc; } -CK_RV des_funcs() +CK_RV des_funcs(void) { int i; CK_RV rv; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/dh_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/dh_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/dh_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/dh_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -513,7 +513,7 @@ return rc; } /* end do_DeriveDHKey() */ -CK_RV dh_functions() +CK_RV dh_functions(void) { CK_RV rv, rv2; CK_MECHANISM_INFO mechinfo; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/digest_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/digest_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/digest_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/digest_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -48,7 +48,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(slot_id, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -57,7 +57,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Starting %s Digest with test vector %d.", + testcase_begin("Starting %s Digest with test vector %u.", tsuite->name, i); rc = CKR_OK; // set rc @@ -98,13 +98,13 @@ if (actual_len != expected_len) { testcase_fail("hashed data length does not match test " "vector's hashed data length.\n expected" - " length=%ld, found length=%ld.", + " length=%lu, found length=%lu.", expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { testcase_fail("hashed data does not match test vector's" " hashed data."); } else { - testcase_pass("%s Digest with test vector %d passed.", + testcase_pass("%s Digest with test vector %u passed.", tsuite->name, i); } } @@ -142,7 +142,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(slot_id, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -151,7 +151,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Starting %s Multipart Digest with test vector %d.", + testcase_begin("Starting %s Multipart Digest with test vector %u.", tsuite->name, i); rc = CKR_OK; // set rc @@ -239,7 +239,7 @@ "test vector's hashed data.\n"); } else { testcase_pass("%s Multipart Digest with test vector " - "%d passed.", tsuite->name, i); + "%u passed.", tsuite->name, i); } } @@ -279,7 +279,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(SLOT_ID, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -288,7 +288,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Sign %s with test vector %d.", tsuite->name, i); + testcase_begin("Sign %s with test vector %u.", tsuite->name, i); /** get mechanism and set parameter **/ mech = tsuite->mech; @@ -351,7 +351,7 @@ if (actual_mac_len != expected_mac_len) { testcase_fail("hashed data length does not match test " "vector's hashed data length\nexpected " - "length=%ld, found length=%ld", + "length=%lu, found length=%lu", expected_mac_len, actual_mac_len); goto error; } else if (memcmp(actual_mac, expected_mac, expected_mac_len)) { @@ -359,7 +359,7 @@ "vector's hashed data"); goto error; } else { - testcase_pass("%s Sign with test vector %d passed", + testcase_pass("%s Sign with test vector %u passed", tsuite->name, i); } error: @@ -407,7 +407,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(SLOT_ID, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -416,7 +416,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Verify %s with test vector %d.", tsuite->name, i); + testcase_begin("Verify %s with test vector %u.", tsuite->name, i); /** get mechanism and set parameter **/ mech = tsuite->mech; @@ -472,7 +472,7 @@ if (rc != CKR_OK) testcase_fail("C_Verify rc=%s", p11_get_ckr(rc)); else - testcase_pass("%s C_Verify with test vector %d passed", + testcase_pass("%s C_Verify with test vector %u passed", tsuite->name, i); error: @@ -521,7 +521,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(SLOT_ID, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -530,7 +530,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Sign %s with test vector %d.", tsuite->name, i); + testcase_begin("Sign %s with test vector %u.", tsuite->name, i); /** get mechanism **/ mech = tsuite->mech; @@ -619,13 +619,13 @@ if (actual_mac_len != expected_mac_len) { testcase_fail("hashed data length does not match test " "vector's hashed data length\nexpected " - "length=%ld, found length=%ld", + "length=%lu, found length=%lu", expected_mac_len, actual_mac_len); } else if (memcmp(actual_mac, expected_mac, expected_mac_len)) { testcase_fail("hashed data does not match test " "vector's hashed data"); } else { - testcase_pass("%s C_Sign with test vector %d passed.", + testcase_pass("%s C_Sign with test vector %u passed.", tsuite->name, i); } error: @@ -672,7 +672,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(SLOT_ID, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -681,7 +681,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Verify %s with test vector %d.", tsuite->name, i); + testcase_begin("Verify %s with test vector %u.", tsuite->name, i); /** get mechanism **/ mech = tsuite->mech; @@ -764,7 +764,7 @@ testcase_fail("C_Verify rc=%s", p11_get_ckr(rc)); else - testcase_pass("%s C_Verify with test vector %d passed.", + testcase_pass("%s C_Verify with test vector %u passed.", tsuite->name, i); error: /** clean up **/ @@ -812,7 +812,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(SLOT_ID, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -821,7 +821,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Multipart SignUpdate %s with test vector %d.", + testcase_begin("Multipart SignUpdate %s with test vector %u.", tsuite->name, i); /** get mechanism and set parameter **/ @@ -949,13 +949,13 @@ if (actual_mac_len != expected_mac_len) { testcase_fail("hashed data length does not match test " "vector's hashed data length\nexpected " - "length=%ld, found length=%ld", + "length=%lu, found length=%lu", expected_mac_len, actual_mac_len); } else if (memcmp(actual_mac, expected_mac, expected_mac_len)) { testcase_fail("hashed data does not match test " "vector's hashed data"); } else { - testcase_pass("%s Sign with test vector %d passed.", + testcase_pass("%s Sign with test vector %u passed.", tsuite->name, i); } @@ -1003,7 +1003,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(SLOT_ID, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -1012,7 +1012,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Multipart VerifyUpdate %s with test vector %d.", + testcase_begin("Multipart VerifyUpdate %s with test vector %u.", tsuite->name, i); /** get mechanism and set parameter **/ @@ -1133,7 +1133,7 @@ if (rc != CKR_OK) testcase_fail("C_VerifyFinal rc=%s", p11_get_ckr(rc)); else - testcase_pass("%s Verfied with test vector %d passed.", + testcase_pass("%s Verfied with test vector %u passed.", tsuite->name, i); error: /** clean up **/ @@ -1186,7 +1186,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(SLOT_ID, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -1195,7 +1195,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Sign Verify %s with test vector %d.", tsuite->name, i); + testcase_begin("Sign Verify %s with test vector %u.", tsuite->name, i); /** get mechanism **/ mech = tsuite->mech; @@ -1205,8 +1205,8 @@ if ((is_ep11_token(SLOT_ID) || is_cca_token(SLOT_ID)) && (!check_supp_keysize(SLOT_ID, mech.mechanism, key_len * 8))) { - testcase_skip("keysize %d is not supported in slot %ld", - (unsigned int) key_len, slot_id); + testcase_skip("keysize %lu is not supported in slot %lu", + key_len, slot_id); continue; } @@ -1276,12 +1276,12 @@ if (actual_len != expected_len) { testcase_fail("hashed data length does not match test " "vector's hashed data length\nexpected length=" - "%ld, found length=%ld", expected_len, actual_len); + "%lu, found length=%lu", expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { testcase_fail("hashed data does not match test " "vector's hashed data"); } else { - testcase_pass("%s Sign Verify with test vector %d " + testcase_pass("%s Sign Verify with test vector %u " "passed.", tsuite->name, i); } @@ -1338,7 +1338,7 @@ /** skip test if mech is not supported with this slot **/ if (!mech_supported(SLOT_ID, tsuite->mech.mechanism)) { testsuite_skip(tsuite->tvcount, - "mechanism %s is not supported with slot %ld", + "mechanism %s is not supported with slot %lu", tsuite->name, slot_id); goto testcase_cleanup; } @@ -1347,7 +1347,7 @@ for (i = 0; i < tsuite->tvcount; i++) { /** begin test **/ - testcase_begin("Multipart Sign Verify %s with test vector %d.", + testcase_begin("Multipart Sign Verify %s with test vector %u.", tsuite->name, i); /** get mechanism **/ @@ -1358,8 +1358,8 @@ if ((is_ep11_token(SLOT_ID) || is_cca_token(SLOT_ID)) && (!check_supp_keysize(SLOT_ID, mech.mechanism, key_len * 8))) { - testcase_skip("keysize %d is not supported in slot %ld", - (unsigned int) key_len, slot_id); + testcase_skip("keysize %lu is not supported in slot %lu", + key_len, slot_id); continue; } @@ -1473,12 +1473,12 @@ if (actual_len != expected_len) { testcase_fail("hashed data length does not match test " "vector's hashed data length\nexpected length=" - "%ld, found length=%ld", expected_len, actual_len); + "%lu, found length=%lu", expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { testcase_fail("hashed data does not match test " "vector's hashed data"); } else { - testcase_pass("%s Sign Verify Multipart with test vector %d " + testcase_pass("%s Sign Verify Multipart with test vector %u " "passed.", tsuite->name, i); } @@ -1535,12 +1535,12 @@ * and also sha1-hmac mechanism */ if (!mech_supported(SLOT_ID, secret_mech.mechanism)) { - testsuite_skip(1, "mechanism %ld not supported with slot %ld", + testsuite_skip(1, "mechanism %lu not supported with slot %lu", secret_mech.mechanism, slot_id); goto testcase_cleanup; } if (!mech_supported(SLOT_ID, hash_mech.mechanism)) { - testsuite_skip(1, "mechanism %ld not supported with slot %ld", + testsuite_skip(1, "mechanism %lu not supported with slot %lu", hash_mech.mechanism, slot_id); goto testcase_cleanup; } @@ -1607,7 +1607,7 @@ return rc; } -CK_RV digest_funcs() +CK_RV digest_funcs(void) { CK_RV rc; unsigned int i; @@ -1656,17 +1656,14 @@ } /** HMAC Multipart tests **/ - /* ica and tpm tokens do not yet support multipart hmac right now. */ - if (!(is_ica_token(SLOT_ID)) && !(is_tpm_token(SLOT_ID))) { - for (i = 0; i < NUM_OF_FIPS_HMAC_TEST_SUITES; i++) { - rc = do_SignUpdate_FIPS_HMAC(&fips_hmac_test_suites[i]); - if (rc && !no_stop) - break; - - rc = do_VerifyUpdate_FIPS_HMAC(&fips_hmac_test_suites[i]); - if (rc && !no_stop) - break; - } + for (i = 0; i < NUM_OF_FIPS_HMAC_TEST_SUITES; i++) { + rc = do_SignUpdate_FIPS_HMAC(&fips_hmac_test_suites[i]); + if (rc && !no_stop) + break; + + rc = do_VerifyUpdate_FIPS_HMAC(&fips_hmac_test_suites[i]); + if (rc && !no_stop) + break; } /* HMAC test with a generated generic secret key */ diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/dilithium_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/dilithium_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/dilithium_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/dilithium_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -21,10 +21,11 @@ #include "defs.h" #include "dilithium.h" #include "mechtable.h" +#include "pqc_oids.h" /** * Experimental Support for Dilithium keys and signatures - * with oid = 1.3.6.1.4.1.2.267.1.6.5 + * with oid = 1.3.6.1.4.1.2.267.xxx * * Only SignInit and Sign(Single) is supported with Dilithium. * SignUpdate/SignFinal are not supported. Same with Verify. @@ -34,14 +35,43 @@ CK_ULONG inputlen; } _signVerifyParam; -_signVerifyParam signVerifyInput[] = { +const _signVerifyParam signVerifyInput[] = { {CKM_IBM_DILITHIUM, 0}, {CKM_IBM_DILITHIUM, 1}, {CKM_IBM_DILITHIUM, 32}, {CKM_IBM_DILITHIUM, 59}, - {CKM_IBM_DILITHIUM, 5900}, + {CKM_IBM_DILITHIUM, 3000}, /* Not all variants support larger sizes */ }; +const CK_BYTE dilithium_r2_65[] = OCK_DILITHIUM_R2_65; +const CK_BYTE dilithium_r2_87[] = OCK_DILITHIUM_R2_87; +const CK_BYTE dilithium_r3_44[] = OCK_DILITHIUM_R3_44; +const CK_BYTE dilithium_r3_65[] = OCK_DILITHIUM_R3_65; +const CK_BYTE dilithium_r3_87[] = OCK_DILITHIUM_R3_87; + +typedef struct variant_info { + const char *name; + CK_ULONG keyform; + const CK_BYTE *oid; + CK_ULONG oid_len; +} _variant_info; + +const _variant_info variants[] = { + { "DEFAULT (DILITHIUM_R2_65)", 0, NULL, 0 }, + { "DILITHIUM_R2_65", CK_IBM_DILITHIUM_KEYFORM_ROUND2_65, + dilithium_r2_65, sizeof(dilithium_r2_65) }, + { "DILITHIUM_R2_87", CK_IBM_DILITHIUM_KEYFORM_ROUND2_87, + dilithium_r2_87, sizeof(dilithium_r2_87) }, + { "DILITHIUM_R3_44", CK_IBM_DILITHIUM_KEYFORM_ROUND3_44, + dilithium_r3_44, sizeof(dilithium_r3_44) }, + { "DILITHIUM_R3_65", CK_IBM_DILITHIUM_KEYFORM_ROUND3_65, + dilithium_r3_65, sizeof(dilithium_r3_65) }, + { "DILITHIUM_R3_87", CK_IBM_DILITHIUM_KEYFORM_ROUND3_87, + dilithium_r3_87, sizeof(dilithium_r3_87) }, +}; + +const CK_ULONG num_variants = sizeof(variants) / sizeof(_variant_info); + CK_RV run_SignVerifyDilithium(CK_SESSION_HANDLE session, CK_MECHANISM_TYPE mechType, CK_ULONG inputlen, @@ -98,7 +128,6 @@ testcase_error("C_Sign rc=%s", p11_get_ckr(rc)); goto testcase_cleanup; } - signature = calloc(sizeof(CK_BYTE), signaturelen); if (signature == NULL) { testcase_error("Can't allocate memory for %lu bytes", @@ -202,7 +231,7 @@ /* Check if calculated signature len matches with known signature len */ if (siglen != dilithium_tv[index].sig_len) { - testcase_error("Calculated signature length %ld does not match known length %ld.", + testcase_error("Calculated signature length %lu does not match known length %lu.", siglen, dilithium_tv[index].sig_len); goto testcase_cleanup; } @@ -236,13 +265,13 @@ return rc; } -CK_RV run_GenerateDilithiumKeyPairSignVerify() +CK_RV run_GenerateDilithiumKeyPairSignVerify(void) { CK_MECHANISM mech; CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; CK_SESSION_HANDLE session; CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; - CK_ULONG user_pin_len, j; + CK_ULONG user_pin_len, j, i; CK_FLAGS flags; CK_MECHANISM_INFO mech_info; CK_RV rc; @@ -260,7 +289,7 @@ rc = funcs->C_GetMechanismInfo(SLOT_ID, mech.mechanism, &mech_info); if (rc != CKR_OK) { if (rc == CKR_MECHANISM_INVALID) { - /* no support for EC key gen? skip */ + /* no support for Dilithium key gen? skip */ testcase_skip("Slot %u doesn't support CKM_IBM_DILITHIUM ", (unsigned int) SLOT_ID); rc = CKR_OK; @@ -271,42 +300,85 @@ } } - /* Setup attributes for public/private Dilithium key */ - CK_BBOOL attr_sign = TRUE; - CK_BBOOL attr_verify = TRUE; - CK_ATTRIBUTE dilithium_attr_private[] = { - {CKA_SIGN, &attr_sign, sizeof(CK_BBOOL)}, - }; - CK_ATTRIBUTE dilithium_attr_public[] = { - {CKA_VERIFY, &attr_verify, sizeof(CK_BBOOL)}, - }; - - /* Generate Dilithium key pair */ - rc = funcs->C_GenerateKeyPair(session, &mech, - dilithium_attr_public, 1, - dilithium_attr_private, 1, - &publ_key, &priv_key); - testcase_new_assertion(); - if (rc != CKR_OK) { - testcase_fail - ("C_GenerateKeyPair with valid input failed, rc=%s", - p11_get_ckr(rc)); - goto testcase_cleanup; - } - testcase_pass("*Generate Dilithium key pair passed."); - - /* Sign/verify with this key pair */ - for (j = 0; j < (sizeof(signVerifyInput) / sizeof(_signVerifyParam)); j++) { + for (i = 0; i < 2 * num_variants; i++) { + /* Setup attributes for public/private Dilithium key */ + CK_BBOOL attr_sign = TRUE; + CK_BBOOL attr_verify = TRUE; + CK_ATTRIBUTE dilithium_attr_private_keyform[] = { + {CKA_SIGN, &attr_sign, sizeof(CK_BBOOL)}, + {CKA_IBM_DILITHIUM_KEYFORM, + (CK_BYTE *)&variants[i % num_variants].keyform, sizeof(CK_ULONG)}, + }; + CK_ATTRIBUTE dilithium_attr_public_keyform[] = { + {CKA_VERIFY, &attr_verify, sizeof(CK_BBOOL)}, + {CKA_IBM_DILITHIUM_KEYFORM, + (CK_BYTE *)&variants[i % num_variants].keyform, sizeof(CK_ULONG)}, + }; + CK_ATTRIBUTE dilithium_attr_private_mode[] = { + {CKA_SIGN, &attr_sign, sizeof(CK_BBOOL)}, + {CKA_IBM_DILITHIUM_MODE, + (CK_BYTE *)variants[i % num_variants].oid, variants[i % num_variants].oid_len}, + }; + CK_ATTRIBUTE dilithium_attr_public_mode[] = { + {CKA_VERIFY, &attr_verify, sizeof(CK_BBOOL)}, + {CKA_IBM_DILITHIUM_MODE, + (CK_BYTE *)variants[i % num_variants].oid, variants[i % num_variants].oid_len}, + }; + CK_ATTRIBUTE *dilithium_attr_private = i < num_variants ? + dilithium_attr_private_keyform : + dilithium_attr_private_mode; + CK_ATTRIBUTE *dilithium_attr_public = i < num_variants ? + dilithium_attr_public_keyform : + dilithium_attr_public_mode; + CK_ULONG num_dilithium_attrs = + (variants[i % num_variants].oid == NULL) ? 1 : 2; + + /* Generate Dilithium key pair */ + rc = funcs->C_GenerateKeyPair(session, &mech, + dilithium_attr_public, num_dilithium_attrs, + dilithium_attr_private, num_dilithium_attrs, + &publ_key, &priv_key); testcase_new_assertion(); - rc = run_SignVerifyDilithium(session, - signVerifyInput[j].mechtype, - signVerifyInput[j].inputlen, - priv_key, publ_key); - if (rc != 0) { - testcase_fail("run_SignVerifyDilithium failed index=%lu.", j); - goto testcase_cleanup; + if (rc != CKR_OK) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_GenerateKeyPair with %s (%s) not supported", + variants[i % num_variants].name, + i < num_variants ? "KEYFORM" : "MODE"); + goto next; + } else { + testcase_fail("C_GenerateKeyPair with %s (%s) and valid input failed, rc=%s", + variants[i % num_variants].name, + i < num_variants ? "KEYFORM" : "MODE", p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + testcase_pass("*Generate Dilithium key pair with %s (%s) passed.", + variants[i % num_variants].name, + i < num_variants ? "KEYFORM" : "MODE"); + + /* Sign/verify with this key pair */ + for (j = 0; j < (sizeof(signVerifyInput) / sizeof(_signVerifyParam)); j++) { + testcase_new_assertion(); + rc = run_SignVerifyDilithium(session, + signVerifyInput[j].mechtype, + signVerifyInput[j].inputlen, + priv_key, publ_key); + if (rc != 0) { + testcase_fail("run_SignVerifyDilithium with %s failed index=%lu.", + variants[i % num_variants].name, j); + goto next; + } + testcase_pass("*Sign & verify with %s j=%lu passed.", + variants[i % num_variants].name, j); } - testcase_pass("*Sign & verify j=%lu passed.", j); + +next: + if (publ_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, publ_key); + publ_key = CK_INVALID_HANDLE; + if (priv_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, priv_key); + priv_key = CK_INVALID_HANDLE; } rc = CKR_OK; @@ -323,7 +395,7 @@ return rc; } -CK_RV run_ImportDilithiumKeyPairSignVerify() +CK_RV run_ImportDilithiumKeyPairSignVerify(void) { CK_MECHANISM mech; CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; @@ -345,7 +417,7 @@ rc = funcs->C_GetMechanismInfo(SLOT_ID, mech.mechanism, &mech_info); if (rc != CKR_OK) { if (rc == CKR_MECHANISM_INVALID) { - /* no support for EC key gen? skip */ + /* no support for Dilithium key gen? skip */ testcase_skip("Slot %u doesn't support CKM_IBM_DILITHIUM", (unsigned int) SLOT_ID); goto testcase_cleanup; @@ -357,10 +429,13 @@ for (i = 0; i < DILITHIUM_TV_NUM; i++) { - testcase_begin("Starting Dilithium import key pair, Sign/Verify, KAT index=%lu", i); + testcase_begin("Starting Dilithium import key pair, Sign/Verify, %s index=%lu", + dilithium_tv[i].name, i); /* Create Dilithium private key */ rc = create_DilithiumPrivateKey(session, + dilithium_tv[i].pkcs8, dilithium_tv[i].pkcs8_len, + dilithium_tv[i].keyform, dilithium_tv[i].rho, dilithium_tv[i].rho_len, dilithium_tv[i].seed, dilithium_tv[i].seed_len, dilithium_tv[i].tr, dilithium_tv[i].tr_len, @@ -371,7 +446,11 @@ &priv_key); testcase_new_assertion(); if (rc != CKR_OK) { - if (rc == CKR_POLICY_VIOLATION) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_CreateObject with %s not supported", + dilithium_tv[i].name); + continue; + } else if (rc == CKR_POLICY_VIOLATION) { testcase_skip("Dilithium key import is not allowed by policy"); continue; } @@ -384,12 +463,18 @@ /* Create Dilithium public key */ rc = create_DilithiumPublicKey(session, + dilithium_tv[i].spki, dilithium_tv[i].spki_len, + dilithium_tv[i].keyform, dilithium_tv[i].rho, dilithium_tv[i].rho_len, dilithium_tv[i].t1, dilithium_tv[i].t1_len, &publ_key); testcase_new_assertion(); if (rc != CKR_OK) { - if (rc == CKR_POLICY_VIOLATION) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_CreateObject with %s not supported", + dilithium_tv[i].name); + goto testcase_cleanup; + } else if (rc == CKR_POLICY_VIOLATION) { testcase_skip("Dilithium key import is not allowed by policy"); goto testcase_cleanup; } @@ -526,7 +611,7 @@ return rc; } -CK_RV run_TransferDilithiumKeyPairSignVerify() +CK_RV run_TransferDilithiumKeyPairSignVerify(void) { CK_MECHANISM mech; CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; @@ -553,7 +638,7 @@ rc = funcs->C_GetMechanismInfo(SLOT_ID, mech.mechanism, &mech_info); if (rc != CKR_OK) { if (rc == CKR_MECHANISM_INVALID) { - /* no support for EC key gen? skip */ + /* no support for Dilithium key gen? skip */ testcase_skip("Slot %u doesn't support CKM_IBM_DILITHIUM", (unsigned int) SLOT_ID); goto testcase_cleanup; @@ -565,10 +650,13 @@ for (i = 0; i < DILITHIUM_TV_NUM; i++) { - testcase_begin("Starting Dilithium transfer key pair, Sign/Verify KAT index=%ld.",i); + testcase_begin("Starting Dilithium transfer key pair, Sign/Verify %s index=%lu.", + dilithium_tv[i].name, i); /* Create Dilithium private key */ rc = create_DilithiumPrivateKey(session, + dilithium_tv[i].pkcs8, dilithium_tv[i].pkcs8_len, + dilithium_tv[i].keyform, dilithium_tv[i].rho, dilithium_tv[i].rho_len, dilithium_tv[i].seed, dilithium_tv[i].seed_len, dilithium_tv[i].tr, dilithium_tv[i].tr_len, @@ -579,7 +667,11 @@ &priv_key); testcase_new_assertion(); if (rc != CKR_OK) { - if (rc == CKR_POLICY_VIOLATION) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_CreateObject with %s not supported", + dilithium_tv[i].name); + continue; + } else if (rc == CKR_POLICY_VIOLATION) { testcase_skip("Dilithium key import is not allowed by policy"); continue; } @@ -593,12 +685,18 @@ /* Create Dilithium public key */ rc = create_DilithiumPublicKey(session, + dilithium_tv[i].spki, dilithium_tv[i].spki_len, + dilithium_tv[i].keyform, dilithium_tv[i].rho, dilithium_tv[i].rho_len, dilithium_tv[i].t1, dilithium_tv[i].t1_len, &publ_key); testcase_new_assertion(); if (rc != CKR_OK) { - if (rc == CKR_POLICY_VIOLATION) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_CreateObject with %s not supported", + dilithium_tv[i].name); + goto testcase_cleanup; + } else if (rc == CKR_POLICY_VIOLATION) { testcase_skip("Dilithium key import is not allowed by policy"); goto testcase_cleanup; } diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/dilithium.h opencryptoki-3.20.0+dfsg/testcases/crypto/dilithium.h --- opencryptoki-3.18.0+dfsg/testcases/crypto/dilithium.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/dilithium.h 2023-02-13 09:22:42.000000000 +0100 @@ -10,7 +10,7 @@ /** * Experimental Support for Dilithium keys and signatures - * with oid = 1.3.6.1.4.1.2.267.1.6.5 + * with oid = 1.3.6.1.4.1.2.267.xxx * * Public-key encoding; raw public-key field. See RFC 3279 for * subjectPublicKeyInfo (SPKI) structures. @@ -41,6 +41,7 @@ struct DILITHIUM_TEST_VECTOR { char *name; int version; + CK_ULONG keyform; CK_ULONG rho_len; CK_BYTE rho[32]; CK_ULONG seed_len; @@ -48,17 +49,21 @@ CK_ULONG tr_len; CK_BYTE tr[48]; CK_ULONG s1_len; - CK_BYTE s1[480]; + CK_BYTE s1[672]; CK_ULONG s2_len; - CK_BYTE s2[576]; + CK_BYTE s2[768]; CK_ULONG t0_len; - CK_BYTE t0[2688]; + CK_BYTE t0[3584]; CK_ULONG t1_len; - CK_BYTE t1[1728]; + CK_BYTE t1[2560]; + CK_BYTE pkcs8[8192]; + CK_ULONG pkcs8_len; + CK_BYTE spki[8192]; + CK_ULONG spki_len; CK_ULONG msg_len; CK_BYTE msg[4096]; // adjust to max msg len CK_ULONG sig_len; - CK_BYTE sig[3366]; + CK_BYTE sig[4668]; }; /** @@ -66,8 +71,372 @@ */ struct DILITHIUM_TEST_VECTOR dilithium_tv[] = { { - .name = "Dilithium 6-5 KAT 0", + .name = "Dilithium Round 2, Level 4 (6-5) KAT 0 (PKCS#8/SPKI)", .version = 0, + .keyform = 0, + .rho_len = 0, + .seed_len = 0, + .tr_len = 0, + .s1_len = 0, + .s2_len = 0, + .t0_len = 0, + .t1_len = 0, + .pkcs8_len = 5652, + .pkcs8 = { + 0x30, 0x82, 0x16, 0x10, 0x02, 0x01, 0x00, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x01, 0x06, 0x05, 0x05, 0x00, 0x04, 0x82, 0x15, 0xf8, 0x30, 0x82, 0x15, 0xf4, + 0x02, 0x01, 0x00, 0x03, 0x21, 0x00, 0x7c, 0x99, 0x35, 0xa0, 0xb0, 0x76, 0x94, 0xaa, 0x0c, 0x6d, 0x10, 0xe4, 0xdb, 0x6b, 0x1a, 0xdd, 0x2f, 0xd8, 0x1a, 0x25, 0xcc, 0xb1, 0x48, 0x03, 0x2d, 0xcd, + 0x73, 0x99, 0x36, 0x73, 0x7f, 0x2d, 0x03, 0x21, 0x00, 0x3e, 0x78, 0x4c, 0xcb, 0x7e, 0xbc, 0xdc, 0xfd, 0x45, 0x54, 0x2b, 0x7f, 0x6a, 0xf7, 0x78, 0x74, 0x2e, 0x0f, 0x44, 0x79, 0x17, 0x50, 0x84, + 0xaa, 0x48, 0x8b, 0x3b, 0x74, 0x34, 0x06, 0x78, 0xaa, 0x03, 0x31, 0x00, 0x73, 0xfd, 0x5e, 0x3f, 0xe6, 0xfb, 0x80, 0xfa, 0x84, 0x71, 0xc0, 0x8c, 0x68, 0x82, 0xf7, 0x1d, 0x86, 0x21, 0x84, 0xc3, + 0x5f, 0x55, 0x76, 0xc0, 0x65, 0x97, 0xd8, 0xdc, 0xfa, 0x36, 0xa8, 0x0b, 0x2c, 0x25, 0x5a, 0x59, 0x9a, 0x55, 0xb0, 0x74, 0xaf, 0x36, 0xe8, 0xdb, 0x79, 0x23, 0xf7, 0x68, 0x03, 0x82, 0x01, 0xe1, + 0x00, 0x91, 0xb4, 0x79, 0x09, 0xc5, 0x15, 0x4e, 0x10, 0xb2, 0x0d, 0x12, 0x0d, 0x98, 0x66, 0x0b, 0x08, 0xab, 0x6c, 0xe8, 0xea, 0x09, 0xa6, 0x36, 0x14, 0xac, 0xe0, 0xc0, 0x41, 0x38, 0x13, 0x11, + 0xc9, 0xd5, 0x14, 0x6a, 0x71, 0xc0, 0xda, 0x41, 0xa2, 0x49, 0x91, 0x6e, 0x6d, 0x12, 0xf2, 0xc2, 0x6a, 0xd2, 0x4c, 0x55, 0x8c, 0x86, 0x61, 0x62, 0x01, 0xd8, 0x32, 0x12, 0xc3, 0x04, 0x24, 0x26, + 0x4b, 0xb2, 0xa2, 0xad, 0xe6, 0xda, 0x2e, 0x36, 0xa9, 0xe8, 0x28, 0x8e, 0x2c, 0xd3, 0xcd, 0x5d, 0x22, 0x6d, 0x66, 0xc6, 0xba, 0x02, 0x0c, 0x31, 0x19, 0x69, 0x43, 0xe4, 0x04, 0x6e, 0x71, 0x67, + 0x89, 0x13, 0x14, 0x74, 0x4a, 0x47, 0xb0, 0x50, 0xc3, 0x61, 0x8d, 0x01, 0x22, 0x2a, 0x5a, 0x6b, 0x6a, 0x34, 0x60, 0x26, 0x00, 0x01, 0x68, 0xa6, 0x89, 0x0d, 0x95, 0x10, 0x20, 0x04, 0x82, 0x0c, + 0x6b, 0x70, 0x94, 0x89, 0x50, 0x73, 0x26, 0xd4, 0xb5, 0x0b, 0x40, 0x48, 0x82, 0x31, 0x12, 0xc2, 0x02, 0x0d, 0xe2, 0x78, 0xd0, 0x20, 0x2e, 0x4a, 0x07, 0x41, 0x58, 0x2c, 0x47, 0x9c, 0xbb, 0x15, + 0x2e, 0x8d, 0x24, 0x73, 0x10, 0xd6, 0xe8, 0x66, 0x01, 0xb3, 0x1c, 0xa5, 0x75, 0xb9, 0xd4, 0xd5, 0x84, 0x4e, 0x08, 0xb9, 0xc9, 0x46, 0xc4, 0x84, 0x26, 0xe9, 0x9a, 0xae, 0x6b, 0x33, 0x94, 0x20, + 0x79, 0x35, 0x16, 0x90, 0x58, 0xd4, 0xb2, 0x5e, 0x46, 0xc7, 0x29, 0x09, 0x47, 0xa0, 0x19, 0xb0, 0x16, 0x2a, 0xc6, 0xe1, 0xc0, 0x42, 0x70, 0x04, 0x62, 0x43, 0xe1, 0xcd, 0x6e, 0x52, 0x25, 0x86, + 0xca, 0x8a, 0x15, 0x51, 0x2c, 0x69, 0xb1, 0x62, 0x12, 0x89, 0xc9, 0x89, 0x15, 0x2c, 0x8d, 0xb1, 0x01, 0x2c, 0x1c, 0xb2, 0x14, 0x05, 0x5b, 0x1b, 0x95, 0xcc, 0x41, 0x29, 0x27, 0xc3, 0x4a, 0xc8, + 0x51, 0xcc, 0x65, 0x19, 0x52, 0x13, 0x5e, 0x38, 0x44, 0x80, 0x8c, 0x32, 0x2b, 0x56, 0xcf, 0x1a, 0x68, 0x0d, 0x80, 0xd3, 0xda, 0x6d, 0xb1, 0xd5, 0xf5, 0x98, 0x50, 0x85, 0x38, 0x30, 0x42, 0x6a, + 0x73, 0x9a, 0x4b, 0xcd, 0x50, 0x35, 0x0d, 0x5b, 0x4b, 0x86, 0x90, 0x22, 0xd8, 0x4e, 0x55, 0xa8, 0x23, 0x9d, 0x15, 0x25, 0x50, 0x35, 0x08, 0x91, 0x31, 0xda, 0x08, 0xcf, 0x2a, 0xb3, 0x15, 0x43, + 0x33, 0xc8, 0x5d, 0x41, 0x59, 0x43, 0xd4, 0x99, 0x30, 0x94, 0x45, 0xd4, 0x3c, 0x60, 0x16, 0xb2, 0x14, 0x45, 0xab, 0xd1, 0xd5, 0x14, 0x7b, 0x85, 0xc8, 0x8a, 0x1b, 0x6c, 0x66, 0x40, 0x49, 0x02, + 0x69, 0xaa, 0x45, 0x83, 0xb2, 0x66, 0x74, 0x81, 0x68, 0x95, 0x2d, 0x51, 0x19, 0x6b, 0x90, 0xab, 0x22, 0x84, 0x55, 0xc9, 0x71, 0xaa, 0x44, 0x00, 0x1c, 0x43, 0xa9, 0x62, 0x47, 0x93, 0x0e, 0xa6, + 0xd2, 0xa2, 0xc6, 0x38, 0xa5, 0x17, 0x2f, 0x4a, 0x25, 0x3a, 0x04, 0xb7, 0x54, 0x91, 0x38, 0x07, 0x42, 0x94, 0x45, 0xf3, 0xa2, 0x45, 0xe8, 0x36, 0xc6, 0x48, 0x8a, 0x08, 0x82, 0x4d, 0x97, 0x1b, + 0xdd, 0x36, 0xac, 0x43, 0x85, 0xd6, 0xd2, 0x4d, 0x5d, 0x88, 0x69, 0x9b, 0xd4, 0x4e, 0x8c, 0x0c, 0xc3, 0xa5, 0x56, 0xb3, 0x54, 0x0a, 0x26, 0x6c, 0x21, 0x6b, 0x5d, 0x3d, 0x52, 0x9e, 0x5d, 0x0d, + 0x9a, 0x00, 0x14, 0x4d, 0x32, 0x08, 0x58, 0x09, 0xd3, 0xd9, 0x38, 0x35, 0x1d, 0xd0, 0xb1, 0x69, 0x29, 0x57, 0x1a, 0x43, 0xc9, 0x32, 0xd3, 0x85, 0xa8, 0x90, 0x0c, 0x6d, 0x1a, 0x2b, 0x74, 0x3a, + 0xb9, 0x03, 0x82, 0x02, 0x41, 0x00, 0x16, 0xa7, 0x65, 0x55, 0x1c, 0x11, 0x1e, 0x95, 0x6c, 0x90, 0x30, 0x79, 0x8b, 0x67, 0x8e, 0x0a, 0x36, 0x72, 0xca, 0x50, 0x27, 0x98, 0xe5, 0x46, 0x6c, 0xa2, + 0x14, 0x16, 0x33, 0x02, 0x11, 0x2c, 0xc3, 0xa9, 0x6d, 0xa3, 0x86, 0xa9, 0xae, 0xa1, 0x10, 0x27, 0x50, 0x08, 0xd9, 0xb3, 0xb9, 0xc0, 0x51, 0x1d, 0x13, 0x9e, 0x5a, 0x66, 0xe0, 0x0c, 0x76, 0x76, + 0x85, 0xa6, 0x0b, 0x12, 0x8f, 0x93, 0xd0, 0x48, 0x02, 0x28, 0x2c, 0x1e, 0x9d, 0x8c, 0x5b, 0x01, 0x14, 0x74, 0x60, 0x66, 0x43, 0xc2, 0x0d, 0x42, 0x1b, 0xa3, 0x8a, 0x44, 0x25, 0x92, 0x44, 0x90, + 0x41, 0x06, 0x8a, 0xa9, 0x24, 0x41, 0xa6, 0x81, 0xd5, 0x05, 0x3a, 0xd4, 0x6c, 0x93, 0x45, 0x5d, 0x8c, 0x18, 0x88, 0xd4, 0x5a, 0x20, 0x3d, 0xaa, 0xcd, 0xa0, 0xa6, 0xac, 0x54, 0x45, 0xb3, 0x0b, + 0x13, 0xb1, 0x61, 0x1a, 0x08, 0x56, 0x6d, 0x6d, 0x8d, 0xa6, 0xda, 0xc0, 0x8d, 0x0d, 0x33, 0xce, 0x99, 0x96, 0xb4, 0x8b, 0xdb, 0x8d, 0xc8, 0x8c, 0x85, 0x6e, 0x03, 0xb2, 0xc1, 0x2c, 0xaa, 0x43, + 0x60, 0x27, 0x60, 0xc1, 0x95, 0x54, 0xca, 0x2e, 0x8d, 0x02, 0x19, 0x83, 0x80, 0x3a, 0x43, 0x1d, 0xcc, 0xd1, 0x82, 0x39, 0x81, 0x90, 0xd1, 0xc2, 0x40, 0xc6, 0x28, 0x6c, 0xb5, 0x8c, 0x6a, 0x15, + 0xea, 0xc8, 0x18, 0x42, 0x6a, 0x6b, 0x01, 0x05, 0x93, 0xb1, 0x53, 0x15, 0xaa, 0xcd, 0x96, 0xcd, 0xc4, 0x79, 0x00, 0x64, 0x8a, 0x24, 0xb6, 0x2e, 0xc6, 0x10, 0xb0, 0x32, 0x38, 0xba, 0x66, 0xa2, + 0x6a, 0xd9, 0x12, 0x2c, 0x74, 0xc9, 0x15, 0x58, 0x44, 0xd1, 0x45, 0xd4, 0xc9, 0x84, 0x6d, 0x97, 0x55, 0x5c, 0x39, 0xdc, 0x40, 0xc2, 0x83, 0xda, 0x46, 0x82, 0x48, 0x33, 0x14, 0x02, 0xa6, 0xb1, + 0x58, 0x78, 0xa3, 0x65, 0x53, 0x8d, 0x25, 0x07, 0xdc, 0x14, 0x5b, 0x73, 0x39, 0xb2, 0x28, 0xb6, 0xd1, 0xb6, 0x54, 0x02, 0x85, 0x9c, 0x00, 0x95, 0x37, 0xd1, 0x6b, 0xb4, 0xa9, 0x32, 0xb9, 0xd5, + 0x0b, 0x44, 0xb4, 0x03, 0x6a, 0x0c, 0xa9, 0x21, 0x4e, 0x81, 0x95, 0x36, 0x0c, 0xc0, 0x72, 0x65, 0x59, 0xc4, 0x09, 0x42, 0x39, 0x93, 0x48, 0xd2, 0x03, 0x44, 0x9b, 0xa5, 0x42, 0xa4, 0xd9, 0x9a, + 0x19, 0xe4, 0x6c, 0x1a, 0xaa, 0xc4, 0x11, 0x1b, 0x41, 0x2d, 0xf3, 0xb0, 0xcc, 0xac, 0x39, 0xa5, 0x19, 0x05, 0x47, 0xa0, 0x51, 0x56, 0x51, 0x57, 0x8c, 0x5b, 0xed, 0xd6, 0x62, 0xda, 0x5a, 0x75, + 0x50, 0x6c, 0x13, 0x11, 0x63, 0x34, 0x52, 0x23, 0x25, 0x46, 0x78, 0x2c, 0x93, 0xc5, 0x20, 0x20, 0x80, 0x59, 0x2a, 0xc2, 0xa4, 0xe6, 0x7a, 0x4e, 0x9c, 0x70, 0xce, 0xa4, 0x8e, 0x86, 0x5d, 0x73, + 0x61, 0xca, 0xd1, 0x13, 0xd2, 0xc5, 0xf6, 0xea, 0x95, 0x2a, 0xb8, 0x6c, 0x90, 0x69, 0x23, 0xab, 0xd5, 0x59, 0x00, 0x52, 0x93, 0x51, 0x59, 0x37, 0x34, 0x2b, 0xba, 0xb0, 0xb4, 0x14, 0x93, 0xe1, + 0xaa, 0xa8, 0x20, 0x08, 0x0e, 0xa9, 0xca, 0x30, 0x51, 0xb1, 0x60, 0xaa, 0xa8, 0x40, 0xc1, 0x3a, 0x5a, 0xc5, 0xb0, 0x02, 0x1a, 0xae, 0x1e, 0x2c, 0x9b, 0x6c, 0xd7, 0x0e, 0x32, 0x39, 0x06, 0x50, + 0x92, 0xa9, 0x71, 0x92, 0x56, 0x02, 0x26, 0xce, 0x9c, 0x41, 0x6e, 0x50, 0x1c, 0x96, 0x4c, 0xa0, 0x7a, 0x13, 0x61, 0x99, 0x01, 0x0b, 0x72, 0x81, 0x45, 0x45, 0x52, 0x1a, 0x0a, 0x6c, 0x31, 0x57, + 0x13, 0x6a, 0x71, 0x42, 0x8d, 0x92, 0xe5, 0x60, 0xc8, 0x99, 0x92, 0x42, 0x9a, 0x91, 0xa6, 0xe9, 0x4a, 0x94, 0xa2, 0x58, 0x33, 0x8e, 0x8a, 0xaa, 0x80, 0xc8, 0x89, 0x23, 0x31, 0x3b, 0x6e, 0x33, + 0x76, 0x44, 0x1b, 0x57, 0x12, 0x10, 0x37, 0xad, 0xa6, 0x36, 0x0e, 0x43, 0xd6, 0x19, 0xbb, 0x58, 0xed, 0xe2, 0x91, 0x83, 0x1a, 0x10, 0x0a, 0xb7, 0xb9, 0x0b, 0xd3, 0x2a, 0x43, 0x5c, 0x4f, 0x34, + 0x18, 0x53, 0xe4, 0xe2, 0x94, 0xde, 0xe4, 0xc1, 0x8a, 0xa5, 0x0a, 0xa5, 0x91, 0x4e, 0x45, 0xb9, 0x6c, 0xe4, 0xc6, 0x4c, 0xaa, 0x64, 0x00, 0x63, 0xdd, 0x1a, 0x33, 0xdc, 0x81, 0x42, 0xc7, 0x0d, + 0x4b, 0x80, 0x82, 0x58, 0x29, 0x93, 0x03, 0x82, 0x0a, 0x81, 0x00, 0x78, 0x81, 0x96, 0x2f, 0x23, 0xe6, 0x5b, 0x5c, 0x42, 0xdd, 0xce, 0x0b, 0x7d, 0x97, 0xd3, 0x53, 0x6b, 0xa3, 0xd9, 0x0b, 0xb3, + 0x6f, 0x47, 0xdb, 0x3f, 0xb1, 0x38, 0xa0, 0x3a, 0x8d, 0xce, 0x07, 0x90, 0x71, 0x65, 0x8b, 0xbb, 0xf2, 0x55, 0x7e, 0x54, 0xd6, 0xfd, 0x7c, 0x88, 0xfb, 0xbd, 0xbd, 0x73, 0x71, 0x03, 0x3c, 0x86, + 0x5f, 0x24, 0x82, 0x1c, 0xb6, 0x86, 0xc7, 0x24, 0xa0, 0x75, 0xf2, 0x34, 0xeb, 0xaf, 0x37, 0xab, 0x7c, 0xdc, 0x57, 0xab, 0xfb, 0xe3, 0x7a, 0xa6, 0x0a, 0x44, 0x29, 0x1c, 0x66, 0x00, 0x8f, 0x22, + 0x4e, 0x3b, 0x1a, 0x0e, 0x5e, 0x17, 0xc5, 0xf3, 0xec, 0xe3, 0x11, 0x23, 0x44, 0x49, 0x90, 0x31, 0xb2, 0x1f, 0x50, 0xed, 0x5b, 0xb5, 0xff, 0x84, 0x0c, 0x13, 0x16, 0x45, 0x6b, 0xdc, 0x82, 0x5e, + 0xb9, 0x03, 0x9a, 0x8f, 0x62, 0x7e, 0x81, 0xa3, 0xbc, 0x39, 0x54, 0xf4, 0xa4, 0xff, 0xf5, 0x73, 0x71, 0xb4, 0x6b, 0x17, 0xf5, 0xb6, 0x84, 0x53, 0x2c, 0xfd, 0xfa, 0x64, 0x7c, 0x73, 0x24, 0x2c, + 0x82, 0xc1, 0x24, 0x4c, 0xc1, 0x41, 0xd3, 0x97, 0x2b, 0x2c, 0xad, 0x88, 0x14, 0xfe, 0x61, 0xec, 0x80, 0xf0, 0x78, 0x3c, 0xe0, 0xc4, 0x19, 0xb6, 0x73, 0x6e, 0xa6, 0xd7, 0xfa, 0xb2, 0x18, 0x95, + 0x01, 0xff, 0x37, 0x78, 0x11, 0x56, 0x03, 0xd9, 0x4a, 0xbf, 0xff, 0x5d, 0x61, 0xe2, 0x81, 0xd8, 0xc1, 0xaf, 0x33, 0x2b, 0x63, 0xf9, 0xca, 0x13, 0x4c, 0xd0, 0x0b, 0xb9, 0x4f, 0x6b, 0x33, 0x67, + 0x2e, 0x92, 0xd4, 0x21, 0xef, 0xda, 0x70, 0x6e, 0x47, 0x04, 0xd3, 0x89, 0x76, 0xe3, 0x39, 0x12, 0x4a, 0x7b, 0xfc, 0x21, 0x85, 0x61, 0xd3, 0xb9, 0x32, 0x5c, 0x09, 0x69, 0xea, 0x0d, 0x0f, 0xd8, + 0x3c, 0x38, 0xd8, 0xf9, 0x84, 0x16, 0xdb, 0x58, 0x5b, 0xf1, 0x6c, 0xaa, 0x1e, 0x11, 0xd8, 0xcf, 0x2b, 0x9a, 0x91, 0x47, 0xa1, 0x14, 0x34, 0x2d, 0x6a, 0x40, 0xaf, 0x35, 0xcb, 0x14, 0x5c, 0xf6, + 0x28, 0x55, 0xad, 0x31, 0x96, 0xbe, 0x6c, 0xa9, 0xb8, 0x8c, 0x88, 0xe3, 0x03, 0x6b, 0x33, 0x00, 0x7b, 0x83, 0x10, 0x67, 0xee, 0x46, 0x08, 0xfd, 0x38, 0xf1, 0x1f, 0x10, 0x2a, 0xcb, 0x30, 0x90, + 0xfe, 0x7c, 0x11, 0x24, 0xf8, 0x16, 0x4f, 0x99, 0xe7, 0x5f, 0xf9, 0x7e, 0xa0, 0xdb, 0xaa, 0x20, 0x78, 0xf5, 0x90, 0x58, 0xdd, 0x9f, 0x4d, 0x15, 0x73, 0xfe, 0xa0, 0xe7, 0x28, 0x60, 0x0a, 0xbb, + 0x63, 0xa9, 0xb9, 0x99, 0xd1, 0xd9, 0x15, 0x27, 0x1c, 0xe7, 0x5b, 0x12, 0x05, 0xa6, 0x20, 0x25, 0x69, 0x1f, 0xa4, 0xf8, 0xad, 0x8a, 0x83, 0x74, 0x94, 0x65, 0x25, 0x81, 0x34, 0x13, 0x1c, 0x01, + 0xbf, 0x3d, 0x43, 0x6a, 0x82, 0x9e, 0xa4, 0xff, 0x36, 0xa4, 0x06, 0xa8, 0x91, 0x2a, 0xb6, 0x04, 0x13, 0xcb, 0x67, 0xe1, 0x27, 0xe6, 0xa1, 0xf3, 0xb6, 0xcf, 0x3d, 0x8c, 0x70, 0xf2, 0xb5, 0x6f, + 0xe4, 0x57, 0x81, 0x6e, 0x17, 0x30, 0x8c, 0x60, 0x05, 0x37, 0x24, 0xd0, 0x97, 0x0f, 0x7f, 0x41, 0xcd, 0x4c, 0xb4, 0xf4, 0x40, 0xbf, 0xe4, 0xe6, 0x0d, 0xf6, 0x88, 0xb5, 0x36, 0xca, 0x57, 0xc8, + 0xf0, 0x15, 0xd8, 0xfd, 0x8d, 0xfd, 0xc4, 0x56, 0x4b, 0xf1, 0x79, 0x40, 0x71, 0x1d, 0xa7, 0x24, 0xa9, 0xb9, 0x86, 0x53, 0x00, 0x58, 0xc4, 0x21, 0x37, 0xd5, 0xce, 0x52, 0x40, 0x1c, 0x26, 0xfa, + 0x59, 0x92, 0x93, 0x96, 0x60, 0xdc, 0x65, 0x2d, 0xf1, 0xdd, 0x91, 0x99, 0x59, 0xc7, 0xd1, 0x15, 0xcd, 0x19, 0x64, 0xb0, 0x4e, 0xf0, 0x3c, 0x30, 0xd1, 0xea, 0x29, 0x47, 0xdc, 0x2e, 0x94, 0x5d, + 0xb8, 0x78, 0xb4, 0xd7, 0x30, 0x27, 0x98, 0xaf, 0xb9, 0x3f, 0x26, 0xea, 0x9a, 0x95, 0xbf, 0x20, 0xef, 0x05, 0x83, 0x7d, 0xf6, 0xdc, 0xc0, 0xd9, 0x62, 0x4b, 0xf0, 0xd4, 0xdf, 0x28, 0xe0, 0xb6, + 0xaf, 0x9d, 0x98, 0xc2, 0x21, 0x96, 0x1a, 0xfe, 0x1e, 0x72, 0x8c, 0x35, 0xaf, 0x7c, 0x6b, 0x42, 0xcc, 0x18, 0x70, 0xac, 0x27, 0xae, 0x90, 0xdb, 0x78, 0xcb, 0x48, 0x85, 0x07, 0xe8, 0x56, 0x1e, + 0x13, 0xd5, 0xb1, 0x72, 0xb2, 0xde, 0x08, 0x66, 0x44, 0xb3, 0x9c, 0x19, 0x44, 0x71, 0x5d, 0x26, 0x31, 0x8e, 0x72, 0xf3, 0x21, 0x91, 0x79, 0x18, 0x6a, 0x9f, 0xe0, 0x2e, 0x41, 0xfe, 0x64, 0xa9, + 0x55, 0xca, 0x04, 0x4d, 0x1d, 0xc7, 0x97, 0xd4, 0x8a, 0x8f, 0x74, 0xdf, 0xf4, 0x17, 0x75, 0x39, 0x02, 0x0e, 0x52, 0x20, 0x7f, 0x01, 0x8d, 0x07, 0xa5, 0xed, 0x88, 0xd7, 0x2d, 0xc6, 0xf1, 0xe9, + 0x2b, 0x36, 0x72, 0x59, 0x4a, 0xee, 0xf3, 0x7e, 0xae, 0x5e, 0xf5, 0xe1, 0xbf, 0xc8, 0x7f, 0x4a, 0x98, 0x36, 0xb2, 0x64, 0x2a, 0x4c, 0x8a, 0xde, 0xdc, 0xc5, 0x1c, 0xf0, 0x70, 0xea, 0x4f, 0xf8, + 0xbf, 0xd8, 0x12, 0x1b, 0x5d, 0x43, 0xad, 0xe5, 0xe1, 0x7e, 0xaf, 0x2c, 0x60, 0xb2, 0x0d, 0x36, 0x11, 0xfd, 0xc3, 0xdf, 0xff, 0x32, 0x14, 0xe3, 0xc6, 0x54, 0xac, 0xb9, 0x7e, 0x0e, 0xe7, 0x2f, + 0x41, 0x6a, 0x50, 0x83, 0xa3, 0x4c, 0x44, 0xb6, 0xe6, 0xc4, 0x4b, 0xc1, 0x0e, 0x92, 0x5f, 0x61, 0x37, 0x0f, 0x18, 0x06, 0xdf, 0x77, 0xcf, 0xc6, 0x8d, 0x40, 0x80, 0x28, 0x52, 0x29, 0x08, 0x7a, + 0xb6, 0xb1, 0x11, 0x5c, 0xab, 0xde, 0x98, 0x2f, 0x11, 0x63, 0xa0, 0xb2, 0x40, 0xaf, 0x6a, 0x5b, 0x94, 0x57, 0xcc, 0xed, 0x75, 0xd2, 0x1b, 0x72, 0xc7, 0x28, 0xba, 0x90, 0x4d, 0x07, 0x39, 0x41, + 0x93, 0xdd, 0x59, 0x6d, 0x75, 0xe3, 0x21, 0x33, 0xdf, 0x3e, 0xaf, 0x89, 0xda, 0x68, 0xad, 0x8a, 0xd1, 0x16, 0xc0, 0x0f, 0x54, 0xd5, 0x51, 0xbe, 0x76, 0x29, 0x82, 0xa2, 0x2a, 0x3d, 0xea, 0xe6, + 0x2d, 0x34, 0xd2, 0x04, 0xd2, 0xcb, 0x06, 0xc1, 0xa8, 0x4e, 0xb4, 0x7a, 0xc9, 0x49, 0x55, 0x13, 0xc1, 0x72, 0x60, 0x20, 0xd8, 0x82, 0x13, 0x50, 0x9c, 0xc8, 0xf0, 0x12, 0xfa, 0x70, 0x4d, 0x2f, + 0xfb, 0xe6, 0xfc, 0xb8, 0xd8, 0x0d, 0x94, 0x7c, 0xfb, 0xd2, 0x0f, 0xef, 0x29, 0x0a, 0xd6, 0x27, 0x18, 0x54, 0x37, 0xd0, 0x24, 0xa9, 0xa1, 0x5e, 0x43, 0x66, 0x24, 0x96, 0x10, 0xbb, 0x75, 0x2d, + 0x4a, 0x86, 0xf5, 0x47, 0x2c, 0x23, 0x46, 0x78, 0x95, 0xf3, 0xad, 0x79, 0xf2, 0x37, 0x17, 0xd1, 0x2f, 0xa1, 0xaf, 0xe1, 0x69, 0x4d, 0x6a, 0x4b, 0x51, 0x8e, 0x7e, 0x03, 0x0a, 0x21, 0x44, 0xd8, + 0x2c, 0xac, 0x65, 0x03, 0xbe, 0x53, 0x56, 0x06, 0x48, 0xd6, 0xea, 0xc3, 0xaa, 0x19, 0x47, 0x01, 0x76, 0x5b, 0x2b, 0xd9, 0xee, 0x9b, 0x2a, 0xaa, 0x53, 0x62, 0xbc, 0x79, 0xa0, 0x2c, 0x2b, 0xf7, + 0x3a, 0xa5, 0x41, 0x1c, 0xbd, 0x04, 0xb9, 0x16, 0xb1, 0x38, 0xfc, 0x7b, 0x0d, 0x55, 0x0e, 0x70, 0x5e, 0x50, 0x3a, 0x42, 0xd3, 0x0b, 0x22, 0x0d, 0x60, 0x8c, 0x83, 0xcf, 0x2e, 0xef, 0x62, 0x79, + 0x50, 0xb8, 0x29, 0xdf, 0x33, 0x44, 0xa6, 0xa9, 0x57, 0xb2, 0x97, 0x18, 0x4b, 0xa6, 0x69, 0xc2, 0x25, 0x0a, 0xd4, 0x29, 0x38, 0xe4, 0xf9, 0x22, 0x92, 0x5f, 0x22, 0x88, 0x7d, 0xf7, 0x9e, 0x95, + 0x43, 0x36, 0xa3, 0xc0, 0xb7, 0x46, 0x22, 0x84, 0xb4, 0xf3, 0x80, 0x11, 0x5c, 0xe7, 0xc3, 0x25, 0x37, 0x64, 0x47, 0x89, 0xf4, 0x2a, 0x31, 0xdb, 0x5c, 0x84, 0x7c, 0xc0, 0x65, 0xa3, 0xdf, 0x03, + 0x54, 0x78, 0x9a, 0x2e, 0x18, 0x49, 0x75, 0x15, 0x1d, 0xfb, 0x96, 0xa9, 0x59, 0x26, 0x97, 0xde, 0xc9, 0xf9, 0xa8, 0xdd, 0xde, 0x89, 0x51, 0x63, 0xbc, 0xfa, 0x48, 0x31, 0x48, 0x5d, 0x2c, 0x98, + 0xfd, 0xa5, 0xc8, 0x3c, 0x7e, 0xea, 0xed, 0xc1, 0xbb, 0x1c, 0x03, 0x81, 0x27, 0xe7, 0x92, 0x91, 0x5a, 0xc5, 0x3d, 0x47, 0x62, 0x8a, 0xf3, 0x8b, 0x30, 0xfc, 0x3b, 0xb9, 0x14, 0xfd, 0x7a, 0x4c, + 0x29, 0x83, 0x3c, 0x94, 0x9e, 0xf1, 0xc0, 0xac, 0x5f, 0xf3, 0xbf, 0x3c, 0x76, 0xc9, 0xf6, 0x59, 0x35, 0x96, 0x52, 0x14, 0x5a, 0xbc, 0xbe, 0xd4, 0x7b, 0xcf, 0x3b, 0xd5, 0x4f, 0xf6, 0x82, 0x45, + 0x2e, 0xd7, 0x51, 0xe2, 0x98, 0x62, 0x93, 0x64, 0xd8, 0x63, 0x3d, 0x24, 0x8b, 0x30, 0x00, 0x96, 0x7c, 0x75, 0x84, 0x7c, 0x61, 0x76, 0x53, 0xcb, 0x44, 0xc5, 0x7c, 0xcf, 0x34, 0xf4, 0xd9, 0xee, + 0xd8, 0x3f, 0xd2, 0x87, 0xa1, 0x1a, 0xb8, 0x6f, 0xfb, 0x4c, 0xa0, 0x1f, 0xd8, 0x2b, 0x04, 0x96, 0xe6, 0xfc, 0xed, 0x8d, 0xc6, 0xd1, 0xf6, 0xc7, 0xdd, 0x1e, 0x2a, 0x8f, 0xf3, 0xc3, 0x1a, 0x36, + 0x1c, 0x77, 0x9d, 0xe7, 0x6f, 0x00, 0x9d, 0x18, 0xef, 0x19, 0x74, 0x3f, 0x1f, 0xff, 0xa6, 0x04, 0x92, 0xbe, 0x1d, 0x01, 0x46, 0xe6, 0xad, 0x13, 0xc3, 0x81, 0x87, 0x0e, 0x6c, 0xdb, 0xde, 0x7e, + 0x5e, 0x71, 0x12, 0x1a, 0x89, 0x26, 0x26, 0xe2, 0xeb, 0xb8, 0x9f, 0x6f, 0x0c, 0x55, 0xc0, 0x4f, 0x9b, 0xcb, 0xaf, 0xb3, 0xf9, 0x05, 0xd4, 0x6d, 0x05, 0x44, 0x10, 0x8c, 0x58, 0x49, 0x7d, 0x44, + 0xc6, 0x40, 0xbc, 0xbf, 0xe3, 0x91, 0xdc, 0xdf, 0xee, 0xee, 0x3d, 0x81, 0x59, 0xe9, 0x73, 0x53, 0xfe, 0x1b, 0x42, 0xf8, 0xd7, 0x09, 0x9e, 0x16, 0xd7, 0x3a, 0x44, 0xf3, 0xa7, 0x07, 0xd0, 0x48, + 0xb1, 0x9c, 0x6f, 0x84, 0xb3, 0x70, 0x44, 0x13, 0x14, 0x56, 0xf6, 0xcf, 0x52, 0x69, 0x4c, 0x5f, 0x39, 0x1e, 0xe3, 0xdd, 0xfd, 0x7c, 0xbe, 0x36, 0x0b, 0x72, 0x99, 0xbc, 0x99, 0xfa, 0xdf, 0xf6, + 0x92, 0xbe, 0xad, 0xbb, 0x31, 0x39, 0x43, 0x33, 0xc1, 0xfa, 0x8d, 0xeb, 0x49, 0x0f, 0xb6, 0x54, 0xea, 0x0c, 0x0e, 0xa9, 0xca, 0x79, 0x8d, 0xf2, 0x86, 0x56, 0xed, 0x4c, 0x60, 0xf6, 0xbd, 0x0c, + 0xb2, 0x41, 0x9b, 0x87, 0xa9, 0x14, 0x9f, 0xc8, 0xea, 0x23, 0x6d, 0xb0, 0x8d, 0x5c, 0xb5, 0xb7, 0xdc, 0x6e, 0x61, 0xa9, 0xec, 0xb0, 0x00, 0x06, 0x02, 0xaf, 0x03, 0xb4, 0x49, 0xe7, 0xab, 0xd9, + 0x2a, 0x9d, 0xf6, 0x42, 0x0c, 0x04, 0x91, 0x24, 0xd7, 0x64, 0x84, 0xc9, 0x22, 0x92, 0x68, 0x91, 0x05, 0x71, 0x74, 0xfc, 0xde, 0xea, 0x07, 0x2f, 0x7d, 0xe3, 0x8e, 0xa3, 0xcf, 0xab, 0x50, 0xac, + 0x5b, 0xd4, 0xaa, 0xd7, 0xca, 0xc3, 0x58, 0x97, 0x72, 0xa1, 0x32, 0xb2, 0x51, 0x0b, 0x62, 0x7a, 0x9e, 0xe1, 0x60, 0xac, 0xb7, 0xa3, 0x55, 0x24, 0xde, 0xe9, 0x49, 0x8b, 0x71, 0xff, 0x65, 0xe9, + 0x62, 0x93, 0x06, 0x93, 0xab, 0x8c, 0xd2, 0x54, 0x84, 0xa5, 0x08, 0x43, 0xfe, 0xe4, 0x84, 0xd6, 0xb6, 0xc1, 0xca, 0x9d, 0x85, 0xf9, 0x7d, 0x80, 0x7d, 0xfe, 0x9e, 0x39, 0x62, 0xc1, 0xf0, 0xee, + 0xfc, 0x00, 0x17, 0x07, 0x64, 0x4b, 0xe2, 0x52, 0x2c, 0xfa, 0x04, 0x26, 0x73, 0x73, 0x93, 0x93, 0x6d, 0x2f, 0xe1, 0xe2, 0x89, 0x75, 0x79, 0xa0, 0x68, 0xfe, 0x29, 0x65, 0xde, 0x40, 0x21, 0x4b, + 0x94, 0xa5, 0x16, 0x08, 0xff, 0xf6, 0xdf, 0x2d, 0x15, 0xdc, 0xe9, 0xa5, 0xb3, 0x0a, 0x11, 0x01, 0x4e, 0xd9, 0x0c, 0x44, 0x46, 0x6f, 0xdf, 0xe0, 0x5c, 0x08, 0x4c, 0x3c, 0x72, 0x47, 0xdf, 0x2c, + 0x72, 0x74, 0xf1, 0x87, 0x9f, 0x39, 0x11, 0x1f, 0x61, 0xbb, 0x98, 0xbb, 0xdb, 0x03, 0x45, 0x8d, 0xfa, 0xba, 0x7d, 0xeb, 0xc7, 0x44, 0xdb, 0x04, 0xcd, 0x84, 0xe8, 0x79, 0xbb, 0xb0, 0xc0, 0x70, + 0xe5, 0x4b, 0x62, 0x96, 0xab, 0x48, 0xd5, 0x11, 0x7f, 0x91, 0x70, 0x01, 0x28, 0xc7, 0x86, 0xb0, 0x1c, 0x89, 0x1c, 0xc0, 0x81, 0x89, 0x6d, 0x40, 0xbf, 0x87, 0x6a, 0x5d, 0x18, 0x22, 0xdd, 0xc3, + 0xf0, 0x6b, 0xca, 0x94, 0x2d, 0x46, 0xd8, 0x49, 0x38, 0x96, 0x55, 0xc8, 0xde, 0xc2, 0xaa, 0xc2, 0xea, 0xf6, 0x1d, 0x11, 0xc7, 0xf7, 0x15, 0x23, 0x36, 0x7e, 0xd4, 0x56, 0x4c, 0x0f, 0x98, 0xd5, + 0xb0, 0x38, 0x66, 0x61, 0x8c, 0x3d, 0xe3, 0x7d, 0x56, 0x6e, 0x8c, 0x0f, 0x8f, 0x7a, 0x56, 0x65, 0x68, 0x87, 0x39, 0x86, 0x1f, 0x78, 0x42, 0x92, 0x57, 0x8b, 0x72, 0x80, 0x3f, 0x7a, 0x4b, 0x8d, + 0x03, 0x18, 0x30, 0xe0, 0xef, 0x94, 0x47, 0x00, 0x9c, 0x83, 0x9f, 0xd6, 0x94, 0xeb, 0x4f, 0x2b, 0x49, 0x08, 0xb8, 0x4d, 0x11, 0xcc, 0x2d, 0xf4, 0x47, 0xa1, 0xc7, 0xb4, 0x84, 0xa6, 0x14, 0x25, + 0x34, 0xd5, 0x62, 0x3e, 0x86, 0xe6, 0xfa, 0xd1, 0x78, 0xa4, 0xa6, 0x0d, 0x4c, 0x8f, 0xe1, 0x1e, 0xe1, 0x53, 0x85, 0xac, 0x79, 0x1b, 0x69, 0x08, 0x48, 0x96, 0xc1, 0xf1, 0x50, 0xd5, 0x0c, 0x24, + 0xf5, 0x07, 0x8f, 0x80, 0xfe, 0xad, 0x9b, 0x4f, 0x51, 0x86, 0x49, 0xb6, 0xb4, 0x09, 0x50, 0x2b, 0x38, 0xe0, 0x7b, 0xef, 0x58, 0x77, 0x35, 0xe8, 0xcb, 0xa9, 0xff, 0x4d, 0x96, 0x85, 0x07, 0x63, + 0xa4, 0x74, 0x37, 0xb2, 0xda, 0x8f, 0x40, 0x72, 0x5e, 0xc6, 0x46, 0xde, 0xc7, 0x27, 0xa8, 0x81, 0x1d, 0x4e, 0x66, 0x8e, 0xa9, 0x7b, 0xc0, 0x23, 0x7f, 0x4e, 0x4a, 0x25, 0xa2, 0xfa, 0x19, 0x8c, + 0x3a, 0x77, 0x4b, 0x57, 0x91, 0x7b, 0x72, 0x07, 0x5a, 0x42, 0x1a, 0x73, 0x90, 0x0b, 0x75, 0x61, 0xee, 0x43, 0x6f, 0x07, 0x75, 0x31, 0x09, 0xf9, 0x22, 0xc0, 0x55, 0x1f, 0x59, 0x1f, 0xb5, 0x46, + 0xa8, 0x81, 0xb1, 0x1c, 0x8c, 0x83, 0x6b, 0xf8, 0x3e, 0xc4, 0x2f, 0xf7, 0x45, 0x1b, 0xf3, 0xe0, 0xcb, 0xc8, 0x7c, 0x97, 0x29, 0x7d, 0x8f, 0xd1, 0x1e, 0x53, 0x44, 0x1e, 0x4b, 0x74, 0x4a, 0xfe, + 0xe4, 0xaa, 0x0b, 0x72, 0x3b, 0x80, 0x6c, 0x34, 0x85, 0xbb, 0xfb, 0x67, 0x31, 0x06, 0x92, 0x05, 0x10, 0x1c, 0xff, 0xcc, 0x2c, 0xe2, 0x63, 0xf3, 0xec, 0xfe, 0x8d, 0x93, 0x0b, 0xf4, 0x9a, 0xd2, + 0x8a, 0x7e, 0x6c, 0xea, 0x75, 0xc5, 0x69, 0x90, 0x6b, 0x5f, 0x93, 0x55, 0x97, 0x1d, 0xf4, 0x03, 0x3d, 0x00, 0x86, 0x65, 0xdd, 0xd0, 0x62, 0x88, 0x11, 0x99, 0x0b, 0x13, 0x04, 0x7a, 0x6b, 0x2e, + 0xec, 0xe1, 0x8c, 0x62, 0x55, 0x82, 0xd6, 0x0e, 0x08, 0x7b, 0x13, 0x47, 0x37, 0xbb, 0xc9, 0x26, 0x03, 0x9c, 0xfa, 0x9c, 0xab, 0xab, 0x8e, 0x3b, 0xd6, 0x31, 0x90, 0x7a, 0x33, 0x1f, 0x1b, 0x08, + 0xc0, 0x9d, 0xca, 0x05, 0xce, 0xb1, 0x49, 0xa0, 0xdf, 0x0e, 0x9a, 0x43, 0x06, 0xa0, 0x49, 0xc9, 0x06, 0x47, 0xc0, 0xee, 0xe7, 0xbf, 0x84, 0xca, 0xf9, 0x1c, 0x1b, 0xe7, 0x1d, 0xf4, 0xa3, 0x23, + 0x69, 0x89, 0x6d, 0xf8, 0xbb, 0x3d, 0xa8, 0xe8, 0x54, 0x4d, 0xd5, 0xc1, 0xd5, 0xcb, 0xa1, 0x34, 0x0b, 0x56, 0xb6, 0xb5, 0x18, 0xaa, 0x62, 0xf9, 0x83, 0xa2, 0x71, 0xba, 0x38, 0x92, 0x04, 0xe1, + 0x95, 0x36, 0xac, 0x98, 0x86, 0x87, 0xa2, 0xdc, 0x0c, 0x5d, 0xec, 0xc1, 0xf0, 0x14, 0x33, 0xb7, 0x01, 0xce, 0x27, 0xb5, 0xca, 0x70, 0x27, 0x38, 0x22, 0xfc, 0x8a, 0x3f, 0x58, 0xe5, 0x22, 0xee, + 0x8b, 0x8b, 0xd0, 0xb7, 0x56, 0x42, 0x72, 0x9d, 0x9d, 0x4c, 0xee, 0xdb, 0xe3, 0xe8, 0xf9, 0x00, 0x69, 0x1a, 0xca, 0x09, 0x6c, 0x92, 0x7a, 0xc3, 0x4e, 0x94, 0xe2, 0xc7, 0xb8, 0x5d, 0x18, 0x74, + 0x5e, 0x42, 0x63, 0xa1, 0x60, 0xfc, 0xc7, 0x87, 0x36, 0x81, 0xf0, 0xdc, 0xc0, 0x36, 0xc1, 0x8d, 0xd0, 0x0f, 0x52, 0x1a, 0x8b, 0x88, 0xd4, 0x8f, 0x71, 0xd2, 0xc5, 0xe7, 0x69, 0xd6, 0xe4, 0x44, + 0x35, 0x70, 0xe9, 0x8c, 0x8c, 0xf6, 0x70, 0xc6, 0xaf, 0x97, 0x46, 0xa8, 0xc2, 0x87, 0xf7, 0x5c, 0xc2, 0x6b, 0xd3, 0x36, 0xbe, 0xec, 0x5a, 0xd8, 0xca, 0x35, 0xd1, 0x67, 0x70, 0xcf, 0x09, 0x3f, + 0xac, 0x78, 0x81, 0xe8, 0x22, 0xaf, 0x2d, 0xad, 0xb7, 0x27, 0x79, 0xab, 0x3e, 0xd8, 0xbc, 0x79, 0x99, 0x95, 0x7c, 0x0d, 0x8a, 0xbd, 0x71, 0xb2, 0x04, 0xf0, 0xfd, 0xbb, 0xac, 0x65, 0x82, 0x17, + 0xe8, 0x83, 0xca, 0xbb, 0x6a, 0xba, 0xc8, 0x0c, 0xf4, 0xba, 0x09, 0x0b, 0x05, 0x71, 0x1b, 0xb3, 0x7b, 0x14, 0x0d, 0xbb, 0x37, 0x4d, 0xa2, 0x89, 0xd7, 0xa9, 0x34, 0x34, 0x49, 0x7d, 0xa9, 0xf8, + 0x16, 0x71, 0x34, 0x57, 0x04, 0xec, 0x03, 0xbb, 0x86, 0x82, 0x52, 0x89, 0x37, 0x3f, 0x72, 0x3c, 0x83, 0x83, 0x13, 0xc8, 0x78, 0x7c, 0x1f, 0xad, 0x57, 0x29, 0xb9, 0xe6, 0x6d, 0xda, 0x71, 0x0d, + 0xd9, 0xfe, 0xb8, 0xb5, 0xba, 0x24, 0x1a, 0x0b, 0xc4, 0x02, 0xdd, 0x9c, 0x30, 0x00, 0x68, 0xf5, 0x0f, 0x94, 0x47, 0x5e, 0xf2, 0xf4, 0xad, 0xd6, 0x67, 0x11, 0x92, 0x07, 0x5a, 0xd2, 0x42, 0x02, + 0xf8, 0xd7, 0x73, 0x66, 0x5c, 0xda, 0x7d, 0x29, 0x79, 0x65, 0x6e, 0xfc, 0x48, 0x94, 0x18, 0xfd, 0x67, 0x99, 0x29, 0xd5, 0xeb, 0x58, 0x4a, 0x6c, 0x18, 0x4d, 0xff, 0xe3, 0xf9, 0x9f, 0x26, 0x71, + 0xd5, 0x4e, 0xc3, 0x48, 0x32, 0x2f, 0xa1, 0xae, 0xc4, 0x67, 0xf5, 0x57, 0x91, 0x22, 0x9f, 0x03, 0x03, 0x53, 0xaf, 0x0f, 0x63, 0x3a, 0x34, 0x59, 0x6e, 0xc0, 0x4c, 0xec, 0x58, 0xc2, 0x50, 0xe0, + 0x99, 0x40, 0xd4, 0x89, 0xef, 0x4b, 0xb5, 0x47, 0x34, 0xf7, 0x64, 0x69, 0x9a, 0x45, 0x3c, 0x43, 0x76, 0x4d, 0x1c, 0xfd, 0x4a, 0x61, 0x8f, 0xc9, 0xed, 0xe9, 0xe3, 0x45, 0x66, 0x3e, 0x9b, 0x20, + 0x89, 0x54, 0xb5, 0x91, 0x8c, 0x61, 0x0d, 0xb7, 0xf5, 0xba, 0xd1, 0xc5, 0xdb, 0x8a, 0x4b, 0xcc, 0xa1, 0xd6, 0x43, 0x92, 0xc7, 0x38, 0x05, 0x36, 0xf0, 0x9c, 0x0a, 0xcc, 0x61, 0xaa, 0xc4, 0x62, + 0x99, 0x44, 0xdc, 0x64, 0x42, 0xe2, 0x30, 0x8c, 0x5a, 0xd7, 0x42, 0x6e, 0x1f, 0xae, 0x75, 0xe8, 0xa3, 0xa0, 0xbb, 0xb7, 0xf3, 0x4f, 0xb4, 0x0f, 0x41, 0x4a, 0xc7, 0x97, 0xe0, 0xb7, 0x0f, 0x69, + 0x65, 0xfc, 0xd3, 0xe0, 0xed, 0x07, 0xda, 0x8b, 0x75, 0x2f, 0x99, 0x2d, 0x3c, 0xd2, 0xc0, 0x58, 0x87, 0x84, 0x85, 0x77, 0xa0, 0x28, 0x12, 0x72, 0x28, 0x69, 0x4a, 0x8d, 0xd5, 0x57, 0x3a, 0x73, + 0x6e, 0xa7, 0xf8, 0x75, 0x06, 0xf9, 0x32, 0xb2, 0xf1, 0x4b, 0x53, 0x86, 0xbd, 0x07, 0x17, 0x04, 0x30, 0x54, 0x82, 0x81, 0x3c, 0xf1, 0x1a, 0xd4, 0x25, 0x0e, 0xc5, 0x79, 0xe8, 0xff, 0x73, 0x4e, + 0x07, 0x95, 0xc5, 0x03, 0xb6, 0x2d, 0x6e, 0x44, 0x7b, 0xed, 0xfd, 0xd1, 0x43, 0x44, 0xe1, 0x8d, 0xd3, 0xfb, 0x95, 0xf0, 0x72, 0xec, 0xf7, 0xc0, 0xe5, 0x51, 0x7c, 0x18, 0xc0, 0xa6, 0x35, 0x26, + 0xda, 0xdd, 0xc9, 0xbc, 0xaf, 0x8b, 0x8b, 0x6a, 0x26, 0x75, 0x58, 0x1b, 0x9d, 0x46, 0x56, 0x3a, 0xda, 0x1c, 0x93, 0xaa, 0x27, 0xf7, 0xa2, 0xf2, 0xc4, 0xb5, 0xee, 0x8a, 0xed, 0x3d, 0x92, 0x5c, + 0x6a, 0x65, 0x47, 0xf6, 0x67, 0x2c, 0x05, 0x8e, 0x5d, 0x95, 0x9b, 0x6b, 0x9e, 0x32, 0x6a, 0xfc, 0x36, 0xe8, 0x9c, 0x14, 0xe6, 0x81, 0x2b, 0x5c, 0xdd, 0xab, 0x38, 0x6b, 0x13, 0xf5, 0xd1, 0x44, + 0x1a, 0x78, 0x98, 0x7b, 0xd1, 0x9e, 0xbe, 0xea, 0x91, 0xef, 0xe4, 0x72, 0xc2, 0xf8, 0xc2, 0x0d, 0xe2, 0x11, 0x73, 0xad, 0xb5, 0xaa, 0xf9, 0x17, 0xc6, 0x03, 0x76, 0xc2, 0x77, 0x6d, 0xd0, 0xc6, + 0x58, 0xe9, 0x48, 0xf3, 0x46, 0xc2, 0xca, 0x2b, 0x77, 0xdc, 0x6b, 0x8b, 0x84, 0xc3, 0x96, 0x78, 0x7e, 0x62, 0xdf, 0x47, 0x0e, 0x94, 0xd8, 0xab, 0x87, 0xca, 0x45, 0x37, 0xce, 0x65, 0x07, 0x0d, + 0xa5, 0xa1, 0xba, 0x4d, 0x22, 0x4d, 0x21, 0x07, 0xff, 0x60, 0x4b, 0x1d, 0x14, 0x25, 0x45, 0x95, 0x8c, 0x11, 0xa3, 0xff, 0xef, 0x36, 0x85, 0x54, 0x69, 0x4f, 0x2b, 0xfa, 0x6b, 0xff, 0x57, 0xf5, + 0x49, 0x98, 0x8c, 0xa9, 0x1e, 0x87, 0xc9, 0xdf, 0xc4, 0x74, 0x76, 0xa0, 0x82, 0x06, 0xc5, 0x03, 0x82, 0x06, 0xc1, 0x00, 0x68, 0x59, 0xf6, 0x4c, 0x66, 0x39, 0x16, 0x79, 0x5e, 0x9d, 0x42, 0xa6, + 0x28, 0xf7, 0xa1, 0x1f, 0xb6, 0xca, 0xd6, 0xbe, 0x5a, 0x22, 0x92, 0x06, 0xf3, 0x8e, 0xc3, 0xe8, 0x7e, 0x74, 0x87, 0xc6, 0x51, 0x27, 0x45, 0xfe, 0xd6, 0xd0, 0xb6, 0x4f, 0x60, 0x55, 0x07, 0xc0, + 0x43, 0xe2, 0x5d, 0x10, 0x3d, 0x19, 0x67, 0x34, 0x93, 0x73, 0x04, 0x73, 0xcd, 0xc0, 0xef, 0x78, 0x0a, 0x83, 0xf2, 0x3a, 0x5c, 0x6c, 0x38, 0x75, 0xbc, 0x10, 0xb6, 0xa0, 0x53, 0xb1, 0x3a, 0xad, + 0x6f, 0xd7, 0xff, 0x1e, 0xcf, 0x8f, 0x72, 0x5f, 0x46, 0x01, 0x81, 0x46, 0x0c, 0x5c, 0x75, 0xe0, 0x50, 0x52, 0xfe, 0xa0, 0xdb, 0xc4, 0x99, 0x2e, 0xe0, 0x43, 0x22, 0xbb, 0x21, 0xaf, 0x25, 0xd7, + 0x84, 0xcb, 0xd4, 0x34, 0xdf, 0x2a, 0x87, 0xaa, 0x48, 0x6a, 0xe7, 0x05, 0x7f, 0xa0, 0x42, 0x87, 0xda, 0x5f, 0xc0, 0xd0, 0x08, 0x8c, 0x16, 0x82, 0xe0, 0x9e, 0x47, 0xab, 0xf3, 0x08, 0x36, 0xc3, + 0x82, 0x42, 0xc8, 0xa4, 0xba, 0x58, 0xfa, 0x4b, 0x7a, 0x17, 0x2d, 0x3b, 0x00, 0x32, 0x51, 0x65, 0x63, 0xfe, 0x46, 0xb7, 0x2e, 0x49, 0xdf, 0xac, 0xd0, 0x03, 0x3e, 0x44, 0x4f, 0x5c, 0xef, 0x0f, + 0xf4, 0x97, 0xd4, 0xd9, 0xd9, 0xe5, 0xb9, 0x88, 0x6f, 0x4b, 0x47, 0x29, 0x9d, 0x63, 0x52, 0x41, 0xa6, 0xdc, 0xf0, 0x69, 0xf1, 0xed, 0x1c, 0x81, 0x5a, 0x51, 0xa6, 0xf7, 0xc7, 0x55, 0xd3, 0xfb, + 0x2c, 0xf0, 0xd6, 0x19, 0xf8, 0x48, 0xc3, 0x5c, 0x5a, 0x61, 0x41, 0x9a, 0x53, 0xcb, 0xa5, 0x19, 0x30, 0x97, 0x43, 0x83, 0x82, 0x8d, 0xad, 0x66, 0x7c, 0x4b, 0x89, 0x01, 0xf7, 0xdf, 0x68, 0xf4, + 0x9f, 0x7f, 0xa2, 0x06, 0x9f, 0x2a, 0xa5, 0xc7, 0xfd, 0xc8, 0x5d, 0x37, 0xd0, 0x66, 0x35, 0x65, 0x71, 0x1d, 0xd1, 0xc5, 0xe6, 0x53, 0x56, 0xdd, 0xfb, 0xe3, 0x4a, 0x67, 0x5c, 0x6f, 0x55, 0xa1, + 0x85, 0xcb, 0xec, 0x69, 0x74, 0x7d, 0x3f, 0x24, 0x8c, 0xc8, 0x1d, 0x1f, 0xb7, 0xd4, 0xbc, 0x6e, 0x3f, 0x78, 0x5a, 0xd0, 0x21, 0x70, 0x01, 0x7d, 0x2a, 0x98, 0x5c, 0x5c, 0xc9, 0xe1, 0x05, 0xcb, + 0x5d, 0xfb, 0x87, 0x86, 0xd4, 0x57, 0x80, 0x13, 0xe7, 0x93, 0xb0, 0xaf, 0x05, 0x75, 0x65, 0xb5, 0xfa, 0xa4, 0xf4, 0x1c, 0x3e, 0xa7, 0x10, 0xc0, 0x19, 0xf8, 0x7d, 0x7e, 0x39, 0xbb, 0xbc, 0x09, + 0x32, 0x01, 0xf7, 0x6e, 0xcb, 0x19, 0xb4, 0xe4, 0xbe, 0x14, 0x90, 0x86, 0x39, 0xe4, 0x46, 0xc3, 0xd1, 0xb1, 0x35, 0x04, 0x8b, 0x72, 0xd3, 0x86, 0x30, 0x93, 0x92, 0x1c, 0xe6, 0x0c, 0x51, 0xc7, + 0x08, 0x13, 0xf6, 0xe8, 0xf0, 0xb0, 0x69, 0x38, 0xb4, 0xaf, 0xa7, 0x96, 0xd1, 0x6f, 0xb6, 0x5f, 0x0c, 0x1b, 0xe6, 0xf2, 0x15, 0xa4, 0xe3, 0xf0, 0x84, 0x6f, 0xc3, 0x9b, 0xd6, 0xd2, 0xc3, 0x3b, + 0xca, 0xdf, 0xff, 0x2a, 0x9e, 0xcd, 0x96, 0x40, 0xdc, 0x3c, 0xbf, 0xee, 0x6f, 0x25, 0x1f, 0xc5, 0x3a, 0x53, 0x50, 0xbf, 0x1b, 0xbc, 0x12, 0xc9, 0x4b, 0x26, 0x3c, 0xd5, 0x89, 0xb5, 0x6a, 0xee, + 0x8a, 0xed, 0x89, 0x1d, 0x34, 0x2b, 0x76, 0xbd, 0x62, 0x15, 0xd9, 0x32, 0x11, 0xef, 0xed, 0x7c, 0x4a, 0x86, 0xba, 0xec, 0x77, 0xbb, 0xe1, 0x18, 0xca, 0xc7, 0x4d, 0xb9, 0xba, 0x42, 0x41, 0xf1, + 0x19, 0xfb, 0x7f, 0x11, 0x15, 0xdd, 0x0a, 0xea, 0x46, 0x5a, 0x83, 0xbf, 0xb0, 0x7d, 0x7f, 0x59, 0x5b, 0x66, 0xa7, 0xeb, 0x25, 0x7b, 0x39, 0x5e, 0x80, 0x45, 0x81, 0xc2, 0x58, 0x85, 0x4b, 0xf7, + 0x64, 0x3f, 0x2b, 0xbc, 0x4a, 0xc2, 0xd2, 0x11, 0x20, 0x70, 0xc3, 0xe6, 0x7b, 0xab, 0x0d, 0x40, 0x67, 0x59, 0xea, 0xe6, 0xeb, 0x90, 0xbe, 0x54, 0xef, 0x92, 0x27, 0xd4, 0xb1, 0x66, 0xad, 0x28, + 0x83, 0x42, 0x22, 0x68, 0x57, 0x65, 0x71, 0x18, 0x77, 0xa7, 0x82, 0x7b, 0x2b, 0xdb, 0xd7, 0xf5, 0xf8, 0xf2, 0x19, 0x92, 0x4a, 0xdd, 0x54, 0xcc, 0x30, 0x24, 0x92, 0x41, 0x82, 0xc5, 0x42, 0xc8, + 0x10, 0x11, 0x02, 0x1d, 0x85, 0x1b, 0x39, 0x72, 0x86, 0xf5, 0x21, 0x1c, 0x82, 0xde, 0xf9, 0xb5, 0x20, 0xf5, 0x64, 0x64, 0x80, 0x5a, 0xd6, 0x5d, 0xbd, 0x8c, 0x60, 0x39, 0xbe, 0x94, 0x86, 0xc0, + 0x72, 0xc0, 0x43, 0x08, 0x05, 0x13, 0x1b, 0xe1, 0xc1, 0xea, 0x43, 0xcc, 0x08, 0xe6, 0xbe, 0x9c, 0xeb, 0x94, 0xab, 0xeb, 0x48, 0xc8, 0xdd, 0x39, 0xa9, 0xde, 0x0b, 0xf0, 0xa3, 0x32, 0xcc, 0x25, + 0xef, 0x1b, 0x36, 0xa3, 0x6b, 0x06, 0xf8, 0x0d, 0x55, 0x9b, 0x46, 0xe2, 0x4d, 0x03, 0x02, 0xe8, 0x2b, 0x81, 0xf1, 0xad, 0xd4, 0x88, 0x49, 0xee, 0xd8, 0x7c, 0x3e, 0x3b, 0xee, 0x7a, 0xf5, 0xcb, + 0xcc, 0x96, 0x01, 0x7e, 0x32, 0xe8, 0xbe, 0x0c, 0x3e, 0xbc, 0x6f, 0x19, 0x87, 0x43, 0x58, 0xce, 0x70, 0xc8, 0x51, 0xad, 0xa6, 0xba, 0x86, 0x85, 0x39, 0x2c, 0x69, 0xb9, 0x06, 0x2c, 0xf7, 0x4d, + 0xb3, 0xc5, 0x3c, 0xbb, 0xe8, 0xe7, 0x78, 0x2b, 0xe7, 0x9e, 0x09, 0x10, 0x0d, 0xe3, 0x21, 0x1d, 0xf2, 0xa5, 0x72, 0x08, 0x31, 0x4b, 0x63, 0x2e, 0xd8, 0x79, 0x9e, 0x42, 0x26, 0xf7, 0xbd, 0x08, + 0x79, 0x02, 0xab, 0xfd, 0x1f, 0x3b, 0xe7, 0x29, 0xf8, 0x60, 0x85, 0x13, 0x32, 0x6f, 0x3f, 0x41, 0x42, 0xd5, 0xa9, 0xcf, 0x3c, 0x19, 0x61, 0x80, 0xa2, 0x3c, 0xbb, 0xbd, 0x37, 0xde, 0x01, 0xc6, + 0x06, 0x4a, 0x75, 0xcb, 0xac, 0x5d, 0xc7, 0x73, 0x15, 0x76, 0x36, 0x6f, 0x3c, 0x70, 0x6e, 0xc2, 0x9e, 0x0e, 0x15, 0xbe, 0xc3, 0x48, 0xa6, 0x07, 0xe2, 0xcf, 0xd4, 0x2a, 0x39, 0x2a, 0xf0, 0xe8, + 0xc4, 0x9d, 0x4b, 0x89, 0xce, 0x05, 0x79, 0xd1, 0x86, 0xf0, 0xc2, 0x2d, 0x84, 0xc5, 0x06, 0x6f, 0x1a, 0x3d, 0xf6, 0x0e, 0xed, 0x66, 0x3d, 0xfa, 0xf6, 0xa3, 0x5a, 0x74, 0x40, 0xd4, 0xc7, 0x68, + 0x53, 0xd7, 0x44, 0xfe, 0x18, 0x6d, 0x98, 0x9f, 0x27, 0x1f, 0x15, 0xc7, 0x0a, 0xd7, 0xa8, 0x60, 0x91, 0xb7, 0x78, 0x67, 0xdd, 0x2c, 0x4f, 0xe5, 0xe2, 0xad, 0x84, 0x3d, 0x7c, 0x99, 0xa6, 0x0b, + 0x70, 0x76, 0x8f, 0x38, 0x44, 0xf5, 0xcc, 0x35, 0x55, 0xf8, 0x19, 0x1b, 0x56, 0xc8, 0xb5, 0xc6, 0x2d, 0x54, 0xd3, 0xde, 0x7b, 0xed, 0x98, 0x01, 0x34, 0xf1, 0x51, 0xd7, 0xe2, 0xce, 0x98, 0x2f, + 0x19, 0x2c, 0x01, 0x08, 0x42, 0xbd, 0x4a, 0xb4, 0x40, 0xee, 0xe9, 0x83, 0x6e, 0x87, 0x2c, 0x8a, 0xef, 0x5e, 0x2b, 0x86, 0x57, 0x8b, 0x36, 0x8c, 0xde, 0x15, 0x96, 0x86, 0x14, 0xea, 0xde, 0xcc, + 0xed, 0xe7, 0x21, 0x79, 0xd4, 0xcc, 0x12, 0x72, 0xea, 0x35, 0xbb, 0x7c, 0xb0, 0x92, 0x50, 0x8c, 0x72, 0x2d, 0x6d, 0xb8, 0xe8, 0xcc, 0x9e, 0x52, 0xc0, 0xe7, 0x07, 0xe4, 0x4a, 0xa0, 0x23, 0x71, + 0x53, 0xae, 0x20, 0xde, 0x9d, 0x7e, 0xd5, 0x79, 0x80, 0xc1, 0xb8, 0x19, 0xf7, 0xb3, 0xa8, 0x59, 0x40, 0x2b, 0x1c, 0xdd, 0xfd, 0x0c, 0x49, 0x18, 0x4b, 0x9a, 0x12, 0x04, 0xa1, 0xd3, 0xdb, 0x63, + 0xff, 0x9d, 0x6a, 0xb7, 0x9b, 0x18, 0xcf, 0xed, 0x0b, 0xdb, 0x76, 0xcc, 0xaa, 0x24, 0xa3, 0xf7, 0xb6, 0xe7, 0x7c, 0xa7, 0x3d, 0x63, 0xf1, 0x5b, 0x2e, 0x98, 0x67, 0x65, 0xd8, 0x68, 0x55, 0xbc, + 0xef, 0x5d, 0x45, 0x3d, 0xea, 0xda, 0x48, 0xc3, 0x0f, 0x48, 0xbd, 0x33, 0xe8, 0xe1, 0x35, 0x11, 0x27, 0x98, 0xfe, 0xc7, 0x44, 0xea, 0xd8, 0x33, 0x8a, 0x77, 0x87, 0xfe, 0x59, 0xe3, 0xb9, 0x08, + 0x89, 0xed, 0x89, 0x63, 0x50, 0x9f, 0x68, 0x02, 0x0f, 0x43, 0x61, 0x92, 0xe9, 0x54, 0x41, 0x12, 0x7e, 0x03, 0xf7, 0x64, 0x32, 0x84, 0x54, 0x76, 0xff, 0x28, 0x4e, 0xe6, 0xf1, 0x62, 0x8c, 0x0f, + 0xec, 0x65, 0xeb, 0xbd, 0x9b, 0x48, 0xf2, 0x02, 0x5f, 0x14, 0x34, 0xe5, 0xa2, 0x23, 0x5f, 0x8f, 0xce, 0x87, 0x3d, 0x8c, 0xca, 0xef, 0x94, 0xc3, 0xba, 0xeb, 0x20, 0x0a, 0x08, 0x00, 0xa6, 0x0b, + 0x9b, 0x1f, 0xfe, 0x72, 0x78, 0xfd, 0x5a, 0x3a, 0xe3, 0x0c, 0x89, 0x34, 0x36, 0xc9, 0xaf, 0x57, 0xd7, 0xe0, 0xd6, 0x25, 0x80, 0xd4, 0x5f, 0x2d, 0xa7, 0x77, 0x0e, 0x49, 0x94, 0xa1, 0x03, 0x1e, + 0x7b, 0xa1, 0xf3, 0x3c, 0xaa, 0x2e, 0x20, 0xec, 0x83, 0x96, 0x60, 0x5f, 0xbd, 0x4c, 0x7b, 0x32, 0xa1, 0xd4, 0x60, 0xb8, 0x7b, 0xbd, 0xc1, 0x93, 0x46, 0x98, 0xe7, 0xf5, 0x71, 0xda, 0x56, 0x08, + 0xdc, 0x1d, 0xa5, 0x80, 0x54, 0xba, 0xa0, 0xb9, 0x83, 0xe0, 0x34, 0x84, 0xcf, 0xbc, 0x32, 0xd0, 0x1c, 0xca, 0x13, 0xbc, 0xf0, 0xca, 0x0c, 0xef, 0xb7, 0x48, 0x03, 0xb9, 0xfd, 0xbe, 0xca, 0x4c, + 0x70, 0x42, 0xb7, 0x28, 0xd2, 0xb7, 0xb3, 0xf4, 0x3c, 0x47, 0xb0, 0xa4, 0x2a, 0xd0, 0xc6, 0xd5, 0x26, 0x2b, 0xc3, 0x98, 0xe7, 0x16, 0x44, 0x8b, 0xb6, 0x8f, 0xae, 0x54, 0x2a, 0x0d, 0x5f, 0x46, + 0x82, 0x0b, 0xd7, 0x8a, 0x61, 0xc3, 0xe8, 0x33, 0xfd, 0x7b, 0xee, 0x3e, 0x39, 0x8f, 0x7c, 0x91, 0xb8, 0x9f, 0x89, 0xe5, 0xeb, 0x12, 0x29, 0x8e, 0xcc, 0x7b, 0xca, 0x64, 0xf9, 0x9f, 0x0a, 0x5f, + 0x48, 0xf5, 0x3f, 0x16, 0x77, 0xee, 0x13, 0xa1, 0xe1, 0xf3, 0x7c, 0x1a, 0x8d, 0xd2, 0x85, 0x58, 0x16, 0x45, 0x9b, 0x3f, 0x14, 0xa1, 0x0c, 0xae, 0x3d, 0x7f, 0x19, 0xe0, 0x41, 0x2a, 0xee, 0xa5, + 0x3b, 0x43, 0x05, 0xf0, 0xd0, 0x22, 0x88, 0x50, 0x60, 0xda, 0x5f, 0x2b, 0x46, 0x65, 0x2d, 0xe2, 0xf5, 0xaf, 0xa8, 0xbf, 0x7e, 0x6c, 0xe5, 0xa6, 0xe4, 0x04, 0x66, 0xc7, 0x92, 0xd3, 0x17, 0x50, + 0xad, 0x28, 0x40, 0x65, 0x1a, 0x44, 0x2b, 0x67, 0x35, 0x37, 0xa7, 0x6e, 0xf4, 0x5f, 0xa1, 0xd3, 0x8f, 0xf7, 0x7e, 0x47, 0x05, 0x21, 0x77, 0x39, 0x92, 0xd5, 0x69, 0x94, 0x12, 0x6e, 0xc9, 0xec, + 0x78, 0x04, 0x73, 0xa0, 0xfd, 0x5a, 0x7e, 0xc9, 0xf3, 0xcf, 0x78, 0x12, 0x56, 0xf4, 0xf1, 0xa9, 0x69, 0x30, 0x15, 0x22, 0x19, 0x3f, 0xd8, 0xcb, 0x8c, 0xcd, 0x5f, 0x94, 0x12, 0x4f, 0x2c, 0x39, + 0xca, 0xe4, 0x55, 0x74, 0x76, 0x1b, 0xd7, 0x6f, 0x64, 0x15, 0x39, 0x34, 0xbd, 0x22, 0x0b, 0x48, 0xfb, 0xd0, 0xfc, 0xb5, 0xd7, 0x39, 0x83, 0x3b, 0x20, 0x3d, 0x55, 0x43, 0x57, 0xc8, 0xb1, 0x91, + 0x9a, 0x46, 0xfd, 0x84, 0xfa, 0x39, 0x64, 0x3f, 0x5e, 0x05, 0x9e, 0xb7, 0x4d, 0x13, 0xf8, 0xb9, 0xd0, 0xe7, 0x73, 0x28, 0x5f, 0xe9, 0xdb, 0x5d, 0x98, 0x56, 0xc1, 0x4d, 0x76, 0xe2, 0x85, 0xcf, + 0xb7, 0xf1, 0xe0, 0x0c, 0xb2, 0x16, 0xcf, 0xda, 0xa9, 0x1f, 0x68, 0x44, 0xdc, 0x08, 0x13, 0xf3, 0xec, 0xb5, 0x36, 0x31, 0xb1, 0xcd, 0x94, 0x19, 0x4a, 0x69, 0x26, 0xb0, 0x1b, 0x35, 0xa3, 0x16, + 0x16, 0x9a, 0x67, 0x2b, 0xcb, 0x96, 0xf3, 0xd3, 0x50, 0x4c, 0xaa, 0xf4, 0xc0, 0x81, 0x32, 0xc1, 0x77, 0xfd, 0x47, 0x38, 0x51, 0x28, 0x23, 0x84, 0x91, 0x47, 0x19, 0x7c, 0x87, 0x3d, 0xf3, 0xc6, + 0xdd, 0x2a, 0xcb, 0xcc, 0xd2, 0x55, 0x7d, 0xd9, 0x64, 0x34, 0x4a, 0xa1, 0x15, 0xc9, 0x47, 0x2f, 0x38, 0xbd, 0x98, 0x96, 0x4a, 0x42, 0x26, 0xef, 0x91, 0x3b, 0x64, 0xb5, 0x40, 0x5d, 0xef, 0xca, + 0x1f, 0x00, 0x8c, 0xba, 0xce, 0xde, 0x3f, 0x63, 0x26, 0xbf, 0x43, 0x66, 0x3e, 0xdd, 0xb7, 0xe5, 0xfc, 0xca, 0x8e, 0xad, 0xa8, 0x86, 0xbc, 0x9d, 0xf4, 0x2e, 0xde, 0x4c, 0xc1, 0x42, 0x9c, 0xd7, + 0xff, 0x4c, 0x9e, 0xed, 0xb2, 0xa2, 0x10, 0xbc, 0x28, 0xae, 0x73, 0xd6, 0x23, 0x3f, 0x6f, 0x65, 0x70, 0x73, 0x9a, 0x0c, 0x53, 0x72, 0x6c, 0x32, 0xe2, 0xe9, 0x5f, 0xca, 0x8c, 0x34, 0xe3, 0x60, + 0x93, 0x72, 0x6a, 0x87, 0x01, 0x3a, 0x35, 0x12, 0xd8, 0x8e, 0xa9, 0x2a, 0x6b, 0x95, 0x7b, 0xf1, 0x0a, 0x6a, 0xee, 0x6e, 0x97, 0x6a, 0xbc, 0xc9, 0x5c, 0x14, 0xa8, 0xef, 0xe6, 0x0a, 0x2c, 0x1a, + 0xf0, 0xab, 0xbe, 0x6b, 0xf7, 0x89, 0xd4, 0xf6, 0x97, 0x38, 0x09, 0x2a, 0xe3, 0xe6, 0x2a, 0xf1, 0x77, 0x3e, 0xd6, 0xa4, 0x2f, 0x1a, 0xaa, 0xbc, 0xfb, 0x98, 0x73, 0x1c, 0xe2, 0x70, 0x1f, 0x42, + 0xe4, 0xba, 0x9e, 0x12, 0x8b, 0x67, 0x26, 0x1c, 0x59, 0x8d, 0x31, 0x89, 0xd0, 0x60, 0x24, 0xf0, 0x1e, 0x25, 0x35, 0x4d, 0x60, 0x32, 0x7f, 0xb6, 0x57, 0x0b, 0xf7, 0xe1, 0x63, 0xfa, 0x04, 0x32, + 0x4b, 0x32, 0xe7, 0xeb, 0xf8, 0xb7, 0x8a, 0xc2, 0xec, 0xfa, 0x3d, 0x36, 0xb1, 0x3a, 0x59, 0xa3, 0xa7, 0x27, 0x02, 0x9b, + }, + .spki_len = 1798, + .spki = { + 0x30, 0x82, 0x07, 0x02, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x01, 0x06, 0x05, 0x05, 0x00, 0x03, 0x82, 0x06, 0xed, 0x00, 0x30, 0x82, 0x06, 0xe8, 0x03, 0x21, + 0x00, 0x7c, 0x99, 0x35, 0xa0, 0xb0, 0x76, 0x94, 0xaa, 0x0c, 0x6d, 0x10, 0xe4, 0xdb, 0x6b, 0x1a, 0xdd, 0x2f, 0xd8, 0x1a, 0x25, 0xcc, 0xb1, 0x48, 0x03, 0x2d, 0xcd, 0x73, 0x99, 0x36, 0x73, 0x7f, + 0x2d, 0x03, 0x82, 0x06, 0xc1, 0x00, 0x68, 0x59, 0xf6, 0x4c, 0x66, 0x39, 0x16, 0x79, 0x5e, 0x9d, 0x42, 0xa6, 0x28, 0xf7, 0xa1, 0x1f, 0xb6, 0xca, 0xd6, 0xbe, 0x5a, 0x22, 0x92, 0x06, 0xf3, 0x8e, + 0xc3, 0xe8, 0x7e, 0x74, 0x87, 0xc6, 0x51, 0x27, 0x45, 0xfe, 0xd6, 0xd0, 0xb6, 0x4f, 0x60, 0x55, 0x07, 0xc0, 0x43, 0xe2, 0x5d, 0x10, 0x3d, 0x19, 0x67, 0x34, 0x93, 0x73, 0x04, 0x73, 0xcd, 0xc0, + 0xef, 0x78, 0x0a, 0x83, 0xf2, 0x3a, 0x5c, 0x6c, 0x38, 0x75, 0xbc, 0x10, 0xb6, 0xa0, 0x53, 0xb1, 0x3a, 0xad, 0x6f, 0xd7, 0xff, 0x1e, 0xcf, 0x8f, 0x72, 0x5f, 0x46, 0x01, 0x81, 0x46, 0x0c, 0x5c, + 0x75, 0xe0, 0x50, 0x52, 0xfe, 0xa0, 0xdb, 0xc4, 0x99, 0x2e, 0xe0, 0x43, 0x22, 0xbb, 0x21, 0xaf, 0x25, 0xd7, 0x84, 0xcb, 0xd4, 0x34, 0xdf, 0x2a, 0x87, 0xaa, 0x48, 0x6a, 0xe7, 0x05, 0x7f, 0xa0, + 0x42, 0x87, 0xda, 0x5f, 0xc0, 0xd0, 0x08, 0x8c, 0x16, 0x82, 0xe0, 0x9e, 0x47, 0xab, 0xf3, 0x08, 0x36, 0xc3, 0x82, 0x42, 0xc8, 0xa4, 0xba, 0x58, 0xfa, 0x4b, 0x7a, 0x17, 0x2d, 0x3b, 0x00, 0x32, + 0x51, 0x65, 0x63, 0xfe, 0x46, 0xb7, 0x2e, 0x49, 0xdf, 0xac, 0xd0, 0x03, 0x3e, 0x44, 0x4f, 0x5c, 0xef, 0x0f, 0xf4, 0x97, 0xd4, 0xd9, 0xd9, 0xe5, 0xb9, 0x88, 0x6f, 0x4b, 0x47, 0x29, 0x9d, 0x63, + 0x52, 0x41, 0xa6, 0xdc, 0xf0, 0x69, 0xf1, 0xed, 0x1c, 0x81, 0x5a, 0x51, 0xa6, 0xf7, 0xc7, 0x55, 0xd3, 0xfb, 0x2c, 0xf0, 0xd6, 0x19, 0xf8, 0x48, 0xc3, 0x5c, 0x5a, 0x61, 0x41, 0x9a, 0x53, 0xcb, + 0xa5, 0x19, 0x30, 0x97, 0x43, 0x83, 0x82, 0x8d, 0xad, 0x66, 0x7c, 0x4b, 0x89, 0x01, 0xf7, 0xdf, 0x68, 0xf4, 0x9f, 0x7f, 0xa2, 0x06, 0x9f, 0x2a, 0xa5, 0xc7, 0xfd, 0xc8, 0x5d, 0x37, 0xd0, 0x66, + 0x35, 0x65, 0x71, 0x1d, 0xd1, 0xc5, 0xe6, 0x53, 0x56, 0xdd, 0xfb, 0xe3, 0x4a, 0x67, 0x5c, 0x6f, 0x55, 0xa1, 0x85, 0xcb, 0xec, 0x69, 0x74, 0x7d, 0x3f, 0x24, 0x8c, 0xc8, 0x1d, 0x1f, 0xb7, 0xd4, + 0xbc, 0x6e, 0x3f, 0x78, 0x5a, 0xd0, 0x21, 0x70, 0x01, 0x7d, 0x2a, 0x98, 0x5c, 0x5c, 0xc9, 0xe1, 0x05, 0xcb, 0x5d, 0xfb, 0x87, 0x86, 0xd4, 0x57, 0x80, 0x13, 0xe7, 0x93, 0xb0, 0xaf, 0x05, 0x75, + 0x65, 0xb5, 0xfa, 0xa4, 0xf4, 0x1c, 0x3e, 0xa7, 0x10, 0xc0, 0x19, 0xf8, 0x7d, 0x7e, 0x39, 0xbb, 0xbc, 0x09, 0x32, 0x01, 0xf7, 0x6e, 0xcb, 0x19, 0xb4, 0xe4, 0xbe, 0x14, 0x90, 0x86, 0x39, 0xe4, + 0x46, 0xc3, 0xd1, 0xb1, 0x35, 0x04, 0x8b, 0x72, 0xd3, 0x86, 0x30, 0x93, 0x92, 0x1c, 0xe6, 0x0c, 0x51, 0xc7, 0x08, 0x13, 0xf6, 0xe8, 0xf0, 0xb0, 0x69, 0x38, 0xb4, 0xaf, 0xa7, 0x96, 0xd1, 0x6f, + 0xb6, 0x5f, 0x0c, 0x1b, 0xe6, 0xf2, 0x15, 0xa4, 0xe3, 0xf0, 0x84, 0x6f, 0xc3, 0x9b, 0xd6, 0xd2, 0xc3, 0x3b, 0xca, 0xdf, 0xff, 0x2a, 0x9e, 0xcd, 0x96, 0x40, 0xdc, 0x3c, 0xbf, 0xee, 0x6f, 0x25, + 0x1f, 0xc5, 0x3a, 0x53, 0x50, 0xbf, 0x1b, 0xbc, 0x12, 0xc9, 0x4b, 0x26, 0x3c, 0xd5, 0x89, 0xb5, 0x6a, 0xee, 0x8a, 0xed, 0x89, 0x1d, 0x34, 0x2b, 0x76, 0xbd, 0x62, 0x15, 0xd9, 0x32, 0x11, 0xef, + 0xed, 0x7c, 0x4a, 0x86, 0xba, 0xec, 0x77, 0xbb, 0xe1, 0x18, 0xca, 0xc7, 0x4d, 0xb9, 0xba, 0x42, 0x41, 0xf1, 0x19, 0xfb, 0x7f, 0x11, 0x15, 0xdd, 0x0a, 0xea, 0x46, 0x5a, 0x83, 0xbf, 0xb0, 0x7d, + 0x7f, 0x59, 0x5b, 0x66, 0xa7, 0xeb, 0x25, 0x7b, 0x39, 0x5e, 0x80, 0x45, 0x81, 0xc2, 0x58, 0x85, 0x4b, 0xf7, 0x64, 0x3f, 0x2b, 0xbc, 0x4a, 0xc2, 0xd2, 0x11, 0x20, 0x70, 0xc3, 0xe6, 0x7b, 0xab, + 0x0d, 0x40, 0x67, 0x59, 0xea, 0xe6, 0xeb, 0x90, 0xbe, 0x54, 0xef, 0x92, 0x27, 0xd4, 0xb1, 0x66, 0xad, 0x28, 0x83, 0x42, 0x22, 0x68, 0x57, 0x65, 0x71, 0x18, 0x77, 0xa7, 0x82, 0x7b, 0x2b, 0xdb, + 0xd7, 0xf5, 0xf8, 0xf2, 0x19, 0x92, 0x4a, 0xdd, 0x54, 0xcc, 0x30, 0x24, 0x92, 0x41, 0x82, 0xc5, 0x42, 0xc8, 0x10, 0x11, 0x02, 0x1d, 0x85, 0x1b, 0x39, 0x72, 0x86, 0xf5, 0x21, 0x1c, 0x82, 0xde, + 0xf9, 0xb5, 0x20, 0xf5, 0x64, 0x64, 0x80, 0x5a, 0xd6, 0x5d, 0xbd, 0x8c, 0x60, 0x39, 0xbe, 0x94, 0x86, 0xc0, 0x72, 0xc0, 0x43, 0x08, 0x05, 0x13, 0x1b, 0xe1, 0xc1, 0xea, 0x43, 0xcc, 0x08, 0xe6, + 0xbe, 0x9c, 0xeb, 0x94, 0xab, 0xeb, 0x48, 0xc8, 0xdd, 0x39, 0xa9, 0xde, 0x0b, 0xf0, 0xa3, 0x32, 0xcc, 0x25, 0xef, 0x1b, 0x36, 0xa3, 0x6b, 0x06, 0xf8, 0x0d, 0x55, 0x9b, 0x46, 0xe2, 0x4d, 0x03, + 0x02, 0xe8, 0x2b, 0x81, 0xf1, 0xad, 0xd4, 0x88, 0x49, 0xee, 0xd8, 0x7c, 0x3e, 0x3b, 0xee, 0x7a, 0xf5, 0xcb, 0xcc, 0x96, 0x01, 0x7e, 0x32, 0xe8, 0xbe, 0x0c, 0x3e, 0xbc, 0x6f, 0x19, 0x87, 0x43, + 0x58, 0xce, 0x70, 0xc8, 0x51, 0xad, 0xa6, 0xba, 0x86, 0x85, 0x39, 0x2c, 0x69, 0xb9, 0x06, 0x2c, 0xf7, 0x4d, 0xb3, 0xc5, 0x3c, 0xbb, 0xe8, 0xe7, 0x78, 0x2b, 0xe7, 0x9e, 0x09, 0x10, 0x0d, 0xe3, + 0x21, 0x1d, 0xf2, 0xa5, 0x72, 0x08, 0x31, 0x4b, 0x63, 0x2e, 0xd8, 0x79, 0x9e, 0x42, 0x26, 0xf7, 0xbd, 0x08, 0x79, 0x02, 0xab, 0xfd, 0x1f, 0x3b, 0xe7, 0x29, 0xf8, 0x60, 0x85, 0x13, 0x32, 0x6f, + 0x3f, 0x41, 0x42, 0xd5, 0xa9, 0xcf, 0x3c, 0x19, 0x61, 0x80, 0xa2, 0x3c, 0xbb, 0xbd, 0x37, 0xde, 0x01, 0xc6, 0x06, 0x4a, 0x75, 0xcb, 0xac, 0x5d, 0xc7, 0x73, 0x15, 0x76, 0x36, 0x6f, 0x3c, 0x70, + 0x6e, 0xc2, 0x9e, 0x0e, 0x15, 0xbe, 0xc3, 0x48, 0xa6, 0x07, 0xe2, 0xcf, 0xd4, 0x2a, 0x39, 0x2a, 0xf0, 0xe8, 0xc4, 0x9d, 0x4b, 0x89, 0xce, 0x05, 0x79, 0xd1, 0x86, 0xf0, 0xc2, 0x2d, 0x84, 0xc5, + 0x06, 0x6f, 0x1a, 0x3d, 0xf6, 0x0e, 0xed, 0x66, 0x3d, 0xfa, 0xf6, 0xa3, 0x5a, 0x74, 0x40, 0xd4, 0xc7, 0x68, 0x53, 0xd7, 0x44, 0xfe, 0x18, 0x6d, 0x98, 0x9f, 0x27, 0x1f, 0x15, 0xc7, 0x0a, 0xd7, + 0xa8, 0x60, 0x91, 0xb7, 0x78, 0x67, 0xdd, 0x2c, 0x4f, 0xe5, 0xe2, 0xad, 0x84, 0x3d, 0x7c, 0x99, 0xa6, 0x0b, 0x70, 0x76, 0x8f, 0x38, 0x44, 0xf5, 0xcc, 0x35, 0x55, 0xf8, 0x19, 0x1b, 0x56, 0xc8, + 0xb5, 0xc6, 0x2d, 0x54, 0xd3, 0xde, 0x7b, 0xed, 0x98, 0x01, 0x34, 0xf1, 0x51, 0xd7, 0xe2, 0xce, 0x98, 0x2f, 0x19, 0x2c, 0x01, 0x08, 0x42, 0xbd, 0x4a, 0xb4, 0x40, 0xee, 0xe9, 0x83, 0x6e, 0x87, + 0x2c, 0x8a, 0xef, 0x5e, 0x2b, 0x86, 0x57, 0x8b, 0x36, 0x8c, 0xde, 0x15, 0x96, 0x86, 0x14, 0xea, 0xde, 0xcc, 0xed, 0xe7, 0x21, 0x79, 0xd4, 0xcc, 0x12, 0x72, 0xea, 0x35, 0xbb, 0x7c, 0xb0, 0x92, + 0x50, 0x8c, 0x72, 0x2d, 0x6d, 0xb8, 0xe8, 0xcc, 0x9e, 0x52, 0xc0, 0xe7, 0x07, 0xe4, 0x4a, 0xa0, 0x23, 0x71, 0x53, 0xae, 0x20, 0xde, 0x9d, 0x7e, 0xd5, 0x79, 0x80, 0xc1, 0xb8, 0x19, 0xf7, 0xb3, + 0xa8, 0x59, 0x40, 0x2b, 0x1c, 0xdd, 0xfd, 0x0c, 0x49, 0x18, 0x4b, 0x9a, 0x12, 0x04, 0xa1, 0xd3, 0xdb, 0x63, 0xff, 0x9d, 0x6a, 0xb7, 0x9b, 0x18, 0xcf, 0xed, 0x0b, 0xdb, 0x76, 0xcc, 0xaa, 0x24, + 0xa3, 0xf7, 0xb6, 0xe7, 0x7c, 0xa7, 0x3d, 0x63, 0xf1, 0x5b, 0x2e, 0x98, 0x67, 0x65, 0xd8, 0x68, 0x55, 0xbc, 0xef, 0x5d, 0x45, 0x3d, 0xea, 0xda, 0x48, 0xc3, 0x0f, 0x48, 0xbd, 0x33, 0xe8, 0xe1, + 0x35, 0x11, 0x27, 0x98, 0xfe, 0xc7, 0x44, 0xea, 0xd8, 0x33, 0x8a, 0x77, 0x87, 0xfe, 0x59, 0xe3, 0xb9, 0x08, 0x89, 0xed, 0x89, 0x63, 0x50, 0x9f, 0x68, 0x02, 0x0f, 0x43, 0x61, 0x92, 0xe9, 0x54, + 0x41, 0x12, 0x7e, 0x03, 0xf7, 0x64, 0x32, 0x84, 0x54, 0x76, 0xff, 0x28, 0x4e, 0xe6, 0xf1, 0x62, 0x8c, 0x0f, 0xec, 0x65, 0xeb, 0xbd, 0x9b, 0x48, 0xf2, 0x02, 0x5f, 0x14, 0x34, 0xe5, 0xa2, 0x23, + 0x5f, 0x8f, 0xce, 0x87, 0x3d, 0x8c, 0xca, 0xef, 0x94, 0xc3, 0xba, 0xeb, 0x20, 0x0a, 0x08, 0x00, 0xa6, 0x0b, 0x9b, 0x1f, 0xfe, 0x72, 0x78, 0xfd, 0x5a, 0x3a, 0xe3, 0x0c, 0x89, 0x34, 0x36, 0xc9, + 0xaf, 0x57, 0xd7, 0xe0, 0xd6, 0x25, 0x80, 0xd4, 0x5f, 0x2d, 0xa7, 0x77, 0x0e, 0x49, 0x94, 0xa1, 0x03, 0x1e, 0x7b, 0xa1, 0xf3, 0x3c, 0xaa, 0x2e, 0x20, 0xec, 0x83, 0x96, 0x60, 0x5f, 0xbd, 0x4c, + 0x7b, 0x32, 0xa1, 0xd4, 0x60, 0xb8, 0x7b, 0xbd, 0xc1, 0x93, 0x46, 0x98, 0xe7, 0xf5, 0x71, 0xda, 0x56, 0x08, 0xdc, 0x1d, 0xa5, 0x80, 0x54, 0xba, 0xa0, 0xb9, 0x83, 0xe0, 0x34, 0x84, 0xcf, 0xbc, + 0x32, 0xd0, 0x1c, 0xca, 0x13, 0xbc, 0xf0, 0xca, 0x0c, 0xef, 0xb7, 0x48, 0x03, 0xb9, 0xfd, 0xbe, 0xca, 0x4c, 0x70, 0x42, 0xb7, 0x28, 0xd2, 0xb7, 0xb3, 0xf4, 0x3c, 0x47, 0xb0, 0xa4, 0x2a, 0xd0, + 0xc6, 0xd5, 0x26, 0x2b, 0xc3, 0x98, 0xe7, 0x16, 0x44, 0x8b, 0xb6, 0x8f, 0xae, 0x54, 0x2a, 0x0d, 0x5f, 0x46, 0x82, 0x0b, 0xd7, 0x8a, 0x61, 0xc3, 0xe8, 0x33, 0xfd, 0x7b, 0xee, 0x3e, 0x39, 0x8f, + 0x7c, 0x91, 0xb8, 0x9f, 0x89, 0xe5, 0xeb, 0x12, 0x29, 0x8e, 0xcc, 0x7b, 0xca, 0x64, 0xf9, 0x9f, 0x0a, 0x5f, 0x48, 0xf5, 0x3f, 0x16, 0x77, 0xee, 0x13, 0xa1, 0xe1, 0xf3, 0x7c, 0x1a, 0x8d, 0xd2, + 0x85, 0x58, 0x16, 0x45, 0x9b, 0x3f, 0x14, 0xa1, 0x0c, 0xae, 0x3d, 0x7f, 0x19, 0xe0, 0x41, 0x2a, 0xee, 0xa5, 0x3b, 0x43, 0x05, 0xf0, 0xd0, 0x22, 0x88, 0x50, 0x60, 0xda, 0x5f, 0x2b, 0x46, 0x65, + 0x2d, 0xe2, 0xf5, 0xaf, 0xa8, 0xbf, 0x7e, 0x6c, 0xe5, 0xa6, 0xe4, 0x04, 0x66, 0xc7, 0x92, 0xd3, 0x17, 0x50, 0xad, 0x28, 0x40, 0x65, 0x1a, 0x44, 0x2b, 0x67, 0x35, 0x37, 0xa7, 0x6e, 0xf4, 0x5f, + 0xa1, 0xd3, 0x8f, 0xf7, 0x7e, 0x47, 0x05, 0x21, 0x77, 0x39, 0x92, 0xd5, 0x69, 0x94, 0x12, 0x6e, 0xc9, 0xec, 0x78, 0x04, 0x73, 0xa0, 0xfd, 0x5a, 0x7e, 0xc9, 0xf3, 0xcf, 0x78, 0x12, 0x56, 0xf4, + 0xf1, 0xa9, 0x69, 0x30, 0x15, 0x22, 0x19, 0x3f, 0xd8, 0xcb, 0x8c, 0xcd, 0x5f, 0x94, 0x12, 0x4f, 0x2c, 0x39, 0xca, 0xe4, 0x55, 0x74, 0x76, 0x1b, 0xd7, 0x6f, 0x64, 0x15, 0x39, 0x34, 0xbd, 0x22, + 0x0b, 0x48, 0xfb, 0xd0, 0xfc, 0xb5, 0xd7, 0x39, 0x83, 0x3b, 0x20, 0x3d, 0x55, 0x43, 0x57, 0xc8, 0xb1, 0x91, 0x9a, 0x46, 0xfd, 0x84, 0xfa, 0x39, 0x64, 0x3f, 0x5e, 0x05, 0x9e, 0xb7, 0x4d, 0x13, + 0xf8, 0xb9, 0xd0, 0xe7, 0x73, 0x28, 0x5f, 0xe9, 0xdb, 0x5d, 0x98, 0x56, 0xc1, 0x4d, 0x76, 0xe2, 0x85, 0xcf, 0xb7, 0xf1, 0xe0, 0x0c, 0xb2, 0x16, 0xcf, 0xda, 0xa9, 0x1f, 0x68, 0x44, 0xdc, 0x08, + 0x13, 0xf3, 0xec, 0xb5, 0x36, 0x31, 0xb1, 0xcd, 0x94, 0x19, 0x4a, 0x69, 0x26, 0xb0, 0x1b, 0x35, 0xa3, 0x16, 0x16, 0x9a, 0x67, 0x2b, 0xcb, 0x96, 0xf3, 0xd3, 0x50, 0x4c, 0xaa, 0xf4, 0xc0, 0x81, + 0x32, 0xc1, 0x77, 0xfd, 0x47, 0x38, 0x51, 0x28, 0x23, 0x84, 0x91, 0x47, 0x19, 0x7c, 0x87, 0x3d, 0xf3, 0xc6, 0xdd, 0x2a, 0xcb, 0xcc, 0xd2, 0x55, 0x7d, 0xd9, 0x64, 0x34, 0x4a, 0xa1, 0x15, 0xc9, + 0x47, 0x2f, 0x38, 0xbd, 0x98, 0x96, 0x4a, 0x42, 0x26, 0xef, 0x91, 0x3b, 0x64, 0xb5, 0x40, 0x5d, 0xef, 0xca, 0x1f, 0x00, 0x8c, 0xba, 0xce, 0xde, 0x3f, 0x63, 0x26, 0xbf, 0x43, 0x66, 0x3e, 0xdd, + 0xb7, 0xe5, 0xfc, 0xca, 0x8e, 0xad, 0xa8, 0x86, 0xbc, 0x9d, 0xf4, 0x2e, 0xde, 0x4c, 0xc1, 0x42, 0x9c, 0xd7, 0xff, 0x4c, 0x9e, 0xed, 0xb2, 0xa2, 0x10, 0xbc, 0x28, 0xae, 0x73, 0xd6, 0x23, 0x3f, + 0x6f, 0x65, 0x70, 0x73, 0x9a, 0x0c, 0x53, 0x72, 0x6c, 0x32, 0xe2, 0xe9, 0x5f, 0xca, 0x8c, 0x34, 0xe3, 0x60, 0x93, 0x72, 0x6a, 0x87, 0x01, 0x3a, 0x35, 0x12, 0xd8, 0x8e, 0xa9, 0x2a, 0x6b, 0x95, + 0x7b, 0xf1, 0x0a, 0x6a, 0xee, 0x6e, 0x97, 0x6a, 0xbc, 0xc9, 0x5c, 0x14, 0xa8, 0xef, 0xe6, 0x0a, 0x2c, 0x1a, 0xf0, 0xab, 0xbe, 0x6b, 0xf7, 0x89, 0xd4, 0xf6, 0x97, 0x38, 0x09, 0x2a, 0xe3, 0xe6, + 0x2a, 0xf1, 0x77, 0x3e, 0xd6, 0xa4, 0x2f, 0x1a, 0xaa, 0xbc, 0xfb, 0x98, 0x73, 0x1c, 0xe2, 0x70, 0x1f, 0x42, 0xe4, 0xba, 0x9e, 0x12, 0x8b, 0x67, 0x26, 0x1c, 0x59, 0x8d, 0x31, 0x89, 0xd0, 0x60, + 0x24, 0xf0, 0x1e, 0x25, 0x35, 0x4d, 0x60, 0x32, 0x7f, 0xb6, 0x57, 0x0b, 0xf7, 0xe1, 0x63, 0xfa, 0x04, 0x32, 0x4b, 0x32, 0xe7, 0xeb, 0xf8, 0xb7, 0x8a, 0xc2, 0xec, 0xfa, 0x3d, 0x36, 0xb1, 0x3a, + 0x59, 0xa3, 0xa7, 0x27, 0x02, 0x9b + }, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 3366, + .sig = { + 0xD7, 0x87, 0x58, 0xC8, 0x99, 0x2B, 0x2D, 0x0F, 0xC5, 0x1A, 0x03, 0xD7, 0x6B, 0x07, 0x17, 0x96, 0xF9, 0x15, 0xD6, 0xB2, 0x41, 0x5F, 0x61, 0x07, 0x58, 0xD1, 0x88, 0xAC, 0x94, 0x04, 0x8C, 0x53, + 0x0D, 0x81, 0xB2, 0xC1, 0xBC, 0x7B, 0x95, 0x19, 0xB3, 0xEB, 0x4F, 0x0C, 0xFA, 0x97, 0xDA, 0x66, 0xB8, 0xD1, 0x44, 0x70, 0x71, 0x1D, 0x1A, 0x85, 0x1A, 0x52, 0xB3, 0x72, 0xC2, 0xBE, 0xB4, 0xA3, + 0xFE, 0xA3, 0x3A, 0x29, 0x3B, 0xC1, 0x83, 0x47, 0xD1, 0x51, 0x47, 0x7D, 0x19, 0x7B, 0xD9, 0x39, 0x7A, 0xB2, 0x74, 0x1A, 0xA6, 0x5E, 0x37, 0xC1, 0x72, 0xEF, 0x29, 0xDD, 0xA2, 0x70, 0x0E, 0xCF, + 0xB9, 0xDF, 0x47, 0x8F, 0xF9, 0x4C, 0xAC, 0x21, 0x6B, 0xDD, 0xD6, 0x7E, 0x2A, 0x52, 0xA2, 0x83, 0x31, 0x2A, 0x2B, 0x09, 0x92, 0x7B, 0xA1, 0x73, 0x7F, 0xBD, 0xEC, 0x13, 0x85, 0x97, 0x83, 0x71, + 0xA1, 0xA1, 0x99, 0x54, 0x3B, 0x8B, 0x36, 0x91, 0x10, 0xEB, 0xE2, 0xB6, 0xDF, 0x44, 0x1A, 0xEE, 0x27, 0xB5, 0x20, 0x7C, 0xDD, 0x3A, 0xF2, 0xF7, 0x71, 0x09, 0xF2, 0xA3, 0xDB, 0x89, 0xD3, 0x00, + 0xE2, 0x7D, 0x9A, 0x48, 0x47, 0x33, 0xF6, 0x08, 0x5D, 0x21, 0xA3, 0xC4, 0xD7, 0xD2, 0x7F, 0x24, 0x37, 0x89, 0xFE, 0xBE, 0x36, 0x1D, 0xE4, 0x82, 0x9C, 0x20, 0x44, 0x1C, 0xD1, 0x93, 0x8E, 0xD9, + 0xF2, 0x83, 0xAC, 0x3C, 0x9A, 0x2D, 0x1F, 0xE8, 0xFE, 0x60, 0x55, 0xED, 0x3C, 0x51, 0x1C, 0x83, 0x07, 0x41, 0x1B, 0x65, 0xDE, 0xCD, 0xFC, 0x6D, 0xDF, 0xB5, 0xEB, 0x0E, 0x1B, 0xDF, 0xC7, 0x0A, + 0xD9, 0x09, 0xEB, 0x11, 0xB3, 0x89, 0x7D, 0xF7, 0x0E, 0x40, 0x65, 0x6E, 0x8D, 0x86, 0x9C, 0x24, 0xC4, 0x39, 0x31, 0x53, 0xF3, 0x8C, 0x7F, 0x58, 0x51, 0xEF, 0xDB, 0x40, 0xD8, 0x02, 0x3F, 0x6D, + 0x37, 0x51, 0x8F, 0xBA, 0xFE, 0x34, 0x44, 0xA8, 0x84, 0xD6, 0xD7, 0x6E, 0x8E, 0x99, 0x54, 0x22, 0xA2, 0x8C, 0xA1, 0x3C, 0x22, 0x32, 0x00, 0xF3, 0xB5, 0x1D, 0xD4, 0xA0, 0x62, 0x34, 0xA6, 0x9F, + 0xAB, 0x90, 0xF3, 0x38, 0x0A, 0x12, 0x5A, 0x63, 0x24, 0x59, 0xE4, 0x89, 0xD9, 0x21, 0x4E, 0x83, 0x7A, 0x16, 0xA8, 0x2D, 0x5F, 0x28, 0x9D, 0xD6, 0x00, 0x06, 0x03, 0x4A, 0xD2, 0xC2, 0xA8, 0x2C, + 0x7E, 0x68, 0x4E, 0xCE, 0xD1, 0x58, 0x4E, 0x95, 0xE6, 0x62, 0x55, 0x07, 0xB1, 0xA6, 0x59, 0xC0, 0xB3, 0x46, 0x3B, 0x9A, 0x11, 0xBB, 0x7C, 0x0A, 0xB6, 0x04, 0x33, 0xA7, 0x85, 0xC9, 0xCC, 0xB7, + 0x94, 0x1D, 0xEA, 0xCB, 0x0B, 0xEB, 0x51, 0x0B, 0x39, 0x50, 0x0A, 0x4C, 0x6E, 0x36, 0xDF, 0x96, 0x4C, 0x82, 0x36, 0x48, 0x1E, 0x73, 0xBD, 0x56, 0x42, 0xCB, 0x10, 0x12, 0xDD, 0x5E, 0x91, 0xD2, + 0xDA, 0x28, 0xBD, 0x29, 0x30, 0x58, 0xB8, 0xC4, 0x9E, 0x81, 0x68, 0xAA, 0x9F, 0x16, 0xEA, 0x45, 0x93, 0x87, 0x31, 0x4C, 0xB6, 0x16, 0x65, 0xCA, 0x62, 0x1D, 0x42, 0xD6, 0x82, 0xA3, 0x48, 0x93, + 0x23, 0xF4, 0x72, 0x84, 0x4B, 0xE5, 0xEB, 0x6D, 0xD1, 0x7A, 0x0B, 0xE4, 0xA1, 0x18, 0x1B, 0x55, 0x57, 0xB3, 0xB4, 0x2F, 0x90, 0x20, 0xDC, 0x3A, 0x7D, 0x1E, 0x55, 0x0C, 0x85, 0xB1, 0xB2, 0xA8, + 0x5F, 0x02, 0x31, 0x2C, 0x01, 0x03, 0xBA, 0x75, 0xB7, 0x09, 0x2C, 0xC1, 0x3A, 0x9C, 0xA6, 0x8A, 0x7B, 0x56, 0xA5, 0x58, 0x28, 0xFD, 0x70, 0x35, 0x64, 0x81, 0xD4, 0xBA, 0x15, 0x6B, 0xAF, 0xFC, + 0xE3, 0xEA, 0x26, 0xC5, 0x91, 0x48, 0x82, 0xF5, 0x5A, 0xB3, 0xFA, 0x73, 0xB4, 0xBF, 0x18, 0x33, 0x0D, 0xB5, 0x48, 0x20, 0x0D, 0x7D, 0xFE, 0x0F, 0xE7, 0xE8, 0x4F, 0xBE, 0x50, 0xB9, 0x9B, 0x37, + 0xEA, 0xBE, 0x32, 0x50, 0xB9, 0x45, 0x8A, 0xBB, 0xA6, 0x01, 0x9E, 0xA5, 0x4A, 0x49, 0x19, 0x0D, 0xCA, 0x0B, 0x62, 0x7C, 0x3D, 0x4F, 0xE4, 0x43, 0xCE, 0xFD, 0x85, 0x28, 0xE4, 0x93, 0xAA, 0xBF, + 0xF8, 0x49, 0x32, 0x67, 0x58, 0x1F, 0xEC, 0xF8, 0x02, 0x74, 0xBE, 0xE4, 0xDC, 0x5B, 0xDF, 0x95, 0x4F, 0xB0, 0x3E, 0xA8, 0xF0, 0x96, 0x3F, 0xED, 0xA3, 0xD1, 0xA1, 0xAE, 0xAE, 0x11, 0x5F, 0xA2, + 0x97, 0x57, 0x6A, 0x12, 0xF9, 0xF2, 0x39, 0x0C, 0x9C, 0xAB, 0x86, 0x9B, 0x22, 0x54, 0x37, 0x64, 0x23, 0x60, 0x72, 0x4F, 0x3F, 0x0A, 0x9F, 0x71, 0x97, 0x9A, 0xE4, 0xE3, 0x03, 0x1E, 0x83, 0xB2, + 0x76, 0x52, 0x63, 0xF4, 0x91, 0x40, 0x0E, 0x9B, 0x90, 0x88, 0x54, 0xB9, 0x16, 0xA1, 0x2F, 0x67, 0x46, 0x5A, 0x46, 0x01, 0xF4, 0x93, 0x2F, 0xA7, 0x11, 0xF1, 0xB0, 0x97, 0xC1, 0x3B, 0x88, 0x6E, + 0x0D, 0xDE, 0xD9, 0xE7, 0xAA, 0xEE, 0x74, 0xFA, 0xDC, 0xDD, 0xF3, 0x8D, 0x61, 0x06, 0x49, 0x55, 0x5E, 0x7A, 0x13, 0xA4, 0xDD, 0x02, 0x84, 0x70, 0x3A, 0x6D, 0x14, 0x7F, 0xDC, 0xE8, 0x6F, 0xC1, + 0xF3, 0x5D, 0xD7, 0x0D, 0xF9, 0xB6, 0x9B, 0xB4, 0xC3, 0xA0, 0x76, 0xBF, 0xA4, 0x6B, 0x05, 0x74, 0x3D, 0xE6, 0x3D, 0xB3, 0x37, 0xD2, 0x0C, 0x14, 0x3C, 0x64, 0x7B, 0x86, 0xCF, 0x8F, 0xF2, 0xE2, + 0x26, 0x7C, 0xC9, 0x5E, 0x0A, 0xC5, 0x57, 0x5D, 0xEF, 0xCD, 0xD2, 0xA5, 0x69, 0x2E, 0xB8, 0x84, 0x50, 0xB3, 0x49, 0x87, 0x78, 0xCA, 0x1F, 0x48, 0xFA, 0x2A, 0x59, 0x03, 0x21, 0xD5, 0x7B, 0x76, + 0xD5, 0x3C, 0x2A, 0x11, 0x29, 0xA3, 0xF2, 0x0B, 0x42, 0xB3, 0xDD, 0xC7, 0xB5, 0xDC, 0x5F, 0xFC, 0xB4, 0xC5, 0xEE, 0xE0, 0xE3, 0xDD, 0x62, 0x9E, 0x38, 0x1C, 0xE8, 0xA9, 0x5A, 0x65, 0xD8, 0xC5, + 0xAD, 0x29, 0xE7, 0x86, 0xDA, 0xA5, 0x8E, 0xA2, 0xC1, 0x29, 0x05, 0xEA, 0xD9, 0xC1, 0x04, 0x06, 0xEC, 0x50, 0xE9, 0xEB, 0x9F, 0xB3, 0x68, 0x2F, 0x1C, 0x33, 0xAD, 0x48, 0x73, 0x0C, 0xDB, 0x6D, + 0x47, 0x73, 0xDE, 0xFE, 0x7D, 0x07, 0xD3, 0xC9, 0xAC, 0xF7, 0xB4, 0x0F, 0x0E, 0x3D, 0x57, 0x2C, 0x0A, 0x10, 0x2D, 0x28, 0xB5, 0x2D, 0xBE, 0xBB, 0xAF, 0x40, 0x3A, 0x25, 0x41, 0x19, 0x64, 0xF3, + 0x55, 0x52, 0xB0, 0xDA, 0x42, 0x80, 0xEA, 0x60, 0xA6, 0x8C, 0x29, 0xA3, 0x1F, 0xD4, 0x99, 0xFF, 0x48, 0x98, 0x7B, 0xD8, 0x32, 0x8E, 0x84, 0x3D, 0xEB, 0xEA, 0x22, 0x21, 0x9B, 0xAB, 0x08, 0x07, + 0xD1, 0x4F, 0x78, 0x34, 0x60, 0x84, 0x70, 0x34, 0xF4, 0xAC, 0x38, 0x81, 0xCA, 0x7C, 0xA6, 0x74, 0xD4, 0x49, 0x98, 0xE0, 0xAC, 0x04, 0xE9, 0x04, 0x2A, 0xAA, 0x1F, 0xA6, 0x74, 0x49, 0x5F, 0xA0, + 0x8B, 0x0D, 0x43, 0xE0, 0x35, 0xCD, 0x6F, 0x18, 0x98, 0x1D, 0x7B, 0x96, 0xBE, 0x61, 0x7C, 0x2F, 0xFF, 0x3F, 0x3B, 0x77, 0x50, 0x74, 0x94, 0x60, 0xA4, 0xBA, 0x17, 0x52, 0xFB, 0x71, 0x37, 0x5B, + 0x10, 0xD9, 0xBE, 0xA5, 0x5B, 0xBE, 0x86, 0xAD, 0x9D, 0x9D, 0xE2, 0x54, 0xDB, 0x42, 0xD7, 0x68, 0x38, 0xFA, 0x81, 0x3A, 0x4D, 0x76, 0x5D, 0x1A, 0x6F, 0x29, 0x02, 0x4D, 0xFC, 0xA6, 0x13, 0xF6, + 0x18, 0xBA, 0x26, 0x3E, 0x97, 0xDB, 0xD0, 0xF4, 0x72, 0xFA, 0x5C, 0x01, 0x14, 0xBE, 0x0E, 0x57, 0xBA, 0x50, 0x58, 0x6D, 0xB3, 0x1B, 0x68, 0x58, 0xA6, 0x26, 0x1E, 0x11, 0xEB, 0x08, 0xAE, 0x66, + 0xEC, 0x3B, 0xF9, 0x70, 0x07, 0xD6, 0x0B, 0x37, 0x31, 0xA1, 0x3A, 0x60, 0xE6, 0xBA, 0xB1, 0x49, 0xC1, 0xFD, 0x1F, 0xD6, 0x60, 0xBB, 0x11, 0x3C, 0x50, 0x2E, 0xCF, 0x67, 0x65, 0x3D, 0xB1, 0xE2, + 0x80, 0xEB, 0xCB, 0x15, 0x22, 0x1C, 0xED, 0x2C, 0x2E, 0xCF, 0x94, 0xC2, 0x29, 0xAD, 0x50, 0x39, 0x4D, 0xD7, 0xCC, 0xFC, 0xE9, 0xB1, 0xF6, 0x40, 0x2D, 0x49, 0xB7, 0xAF, 0xE3, 0x7E, 0xF3, 0x27, + 0x0B, 0x19, 0xA7, 0x28, 0xD4, 0x5B, 0xE7, 0xDB, 0x71, 0x6C, 0x86, 0xA6, 0x84, 0x3F, 0xB9, 0x64, 0xFD, 0xEB, 0xD7, 0xA6, 0xFE, 0x30, 0xE8, 0xF3, 0x0F, 0x1F, 0x3A, 0x79, 0x31, 0xF6, 0x85, 0x29, + 0xC0, 0xCE, 0x9B, 0xA4, 0x75, 0x02, 0x32, 0xE0, 0x52, 0xFE, 0x8B, 0x61, 0x22, 0x1A, 0xED, 0x89, 0x0B, 0xF4, 0x9D, 0x15, 0xBD, 0xA3, 0x36, 0x8F, 0x09, 0x6A, 0x9E, 0x08, 0x8F, 0x94, 0x75, 0xD5, + 0x40, 0x3C, 0xCD, 0x26, 0x7B, 0x9C, 0x5B, 0xE5, 0x2A, 0x54, 0xBA, 0x81, 0x8B, 0xC6, 0xD9, 0x9B, 0x4D, 0x38, 0x3F, 0x1A, 0xDB, 0x58, 0x89, 0xCC, 0xBD, 0x29, 0xE2, 0x26, 0x8C, 0x35, 0x26, 0xE5, + 0x85, 0x31, 0x95, 0xDE, 0x86, 0x11, 0x9F, 0x21, 0x76, 0xEF, 0x1A, 0x25, 0x90, 0x6E, 0x8E, 0x74, 0xB0, 0x46, 0xE6, 0xFA, 0x42, 0xB4, 0x66, 0xBA, 0x0D, 0x5B, 0x21, 0x7C, 0x14, 0x74, 0xF6, 0x75, + 0x6C, 0x8F, 0x87, 0x44, 0x69, 0xCD, 0x9F, 0x1D, 0x41, 0x15, 0x1B, 0xAC, 0x70, 0x62, 0x08, 0x84, 0xD3, 0x35, 0x4F, 0x22, 0xF7, 0x44, 0x14, 0x53, 0x59, 0x0A, 0x6B, 0x93, 0x4F, 0x1B, 0xC6, 0xB5, + 0x61, 0x39, 0x83, 0x0D, 0xAB, 0x8E, 0xE9, 0x71, 0xEF, 0xD0, 0xC1, 0x61, 0xA9, 0xD0, 0xF2, 0x83, 0xF3, 0x44, 0xA4, 0x23, 0x27, 0xFA, 0x53, 0x2D, 0x1E, 0x45, 0x23, 0xC5, 0xC2, 0xA1, 0x2A, 0x80, + 0x1E, 0x0F, 0x92, 0x35, 0x13, 0xFD, 0x7C, 0xB7, 0x35, 0xE3, 0xB2, 0xB2, 0x50, 0xCF, 0x54, 0x14, 0x44, 0x51, 0x5E, 0xCE, 0x10, 0xF6, 0xED, 0x7C, 0x3A, 0xA4, 0x1D, 0xBA, 0xB0, 0xF4, 0xE2, 0xD0, + 0x0F, 0x6A, 0x32, 0xB2, 0xB2, 0xFF, 0xD8, 0x6F, 0xD5, 0xF4, 0xFE, 0x1A, 0x10, 0xC7, 0xDD, 0x10, 0xBE, 0xA3, 0x1B, 0xE8, 0xEB, 0x9B, 0x82, 0xCF, 0x72, 0xC2, 0x00, 0x15, 0x6F, 0xE5, 0x37, 0x37, + 0xBF, 0x00, 0x31, 0x74, 0xFF, 0xBC, 0x72, 0xA0, 0x9C, 0x10, 0xB4, 0xA4, 0x35, 0x13, 0x5D, 0xCD, 0xE5, 0x75, 0xB0, 0x56, 0x22, 0x9C, 0xCB, 0xD2, 0x6A, 0x11, 0x1A, 0xB4, 0x5E, 0x3F, 0x86, 0x4A, + 0xBF, 0xEF, 0x43, 0x14, 0x86, 0xC8, 0xA4, 0x71, 0xA2, 0x27, 0xF5, 0x14, 0x81, 0x9B, 0x0B, 0x13, 0x9C, 0x4C, 0x72, 0x98, 0xB5, 0xD8, 0x07, 0x95, 0x3E, 0x86, 0x40, 0xFE, 0xDE, 0x28, 0x4F, 0x1A, + 0x96, 0xA8, 0x32, 0xAB, 0xA1, 0x10, 0x00, 0xAB, 0x72, 0x6D, 0x30, 0xD3, 0xCB, 0x0C, 0xB7, 0x79, 0xE5, 0x50, 0x45, 0x72, 0xF2, 0xDA, 0xFA, 0xF8, 0x2E, 0x59, 0xB8, 0x19, 0x38, 0x0B, 0x4C, 0xEC, + 0xD1, 0x7B, 0xC7, 0xC3, 0x3B, 0xBA, 0x1E, 0x64, 0x52, 0x1D, 0xB2, 0xD2, 0x38, 0x74, 0x3C, 0x5A, 0x63, 0x75, 0x81, 0x78, 0x29, 0x41, 0x5B, 0x97, 0xDA, 0xD1, 0x34, 0xAC, 0x40, 0x0A, 0xA0, 0xE4, + 0x1B, 0x8B, 0x27, 0x36, 0x47, 0x56, 0xAE, 0xF8, 0x32, 0xE8, 0x8E, 0x5A, 0x29, 0x71, 0xDB, 0x85, 0x79, 0x28, 0x52, 0xDF, 0x55, 0xA7, 0xE8, 0x52, 0x7D, 0x42, 0xB4, 0xC1, 0xAB, 0x8F, 0x80, 0xA3, + 0x84, 0xA8, 0xF3, 0x7C, 0x09, 0x50, 0x41, 0x5B, 0xE7, 0x15, 0x79, 0x5C, 0x88, 0x4C, 0x88, 0x2F, 0xDE, 0xA1, 0x11, 0xF6, 0x67, 0xD4, 0x65, 0x6C, 0x10, 0xA5, 0xCF, 0x5A, 0xF6, 0xBE, 0xB5, 0xBE, + 0x27, 0xFA, 0xB2, 0xD6, 0xDD, 0xC4, 0x81, 0xEF, 0xA7, 0x4A, 0xA7, 0x8F, 0xA5, 0x66, 0xE8, 0x37, 0xEF, 0xDE, 0x77, 0xBC, 0xCF, 0x78, 0x5E, 0xD7, 0xCA, 0xD6, 0x4B, 0x1E, 0x1F, 0xD5, 0x19, 0xF3, + 0x82, 0x60, 0x74, 0xB4, 0xD2, 0x86, 0x77, 0xB0, 0xB1, 0xB9, 0x9A, 0x1D, 0x46, 0xE7, 0xFF, 0x70, 0x75, 0xD2, 0x44, 0x78, 0xD3, 0x7E, 0xA5, 0x43, 0x0C, 0x6E, 0xE8, 0xC5, 0x01, 0xBF, 0xF4, 0xE8, + 0x70, 0x3F, 0x06, 0x5B, 0x83, 0x60, 0x1B, 0x31, 0xB9, 0x0D, 0xE5, 0x01, 0x4A, 0xD4, 0x55, 0x8B, 0xF8, 0x80, 0x69, 0x90, 0xED, 0xDC, 0xC8, 0x50, 0x84, 0xA0, 0xAC, 0xCD, 0xC1, 0x49, 0x7C, 0x8C, + 0x69, 0x9F, 0x8B, 0x0C, 0x75, 0x74, 0x3B, 0x66, 0xFB, 0x4E, 0x2A, 0xE7, 0x99, 0xA0, 0xBD, 0x3A, 0x9C, 0x3F, 0x22, 0x97, 0x48, 0x7B, 0x86, 0x33, 0x4A, 0x73, 0xA9, 0x09, 0xFD, 0xD7, 0x88, 0xE9, + 0xCC, 0x02, 0xFA, 0xAB, 0x77, 0x57, 0xEE, 0xE5, 0x97, 0x89, 0x6C, 0x9C, 0xD3, 0x10, 0xBE, 0x5F, 0x3E, 0x4F, 0xFD, 0xA8, 0x04, 0x47, 0xEB, 0x4C, 0x4E, 0x58, 0xEF, 0xCB, 0x00, 0x90, 0x8B, 0xAA, + 0xB3, 0xF3, 0x64, 0x52, 0x23, 0x19, 0x69, 0x73, 0x43, 0x9A, 0xFA, 0xAF, 0x53, 0x39, 0x85, 0xAB, 0x81, 0x3B, 0x2E, 0x19, 0x78, 0xB3, 0xAD, 0x7A, 0x19, 0x00, 0xD9, 0xCB, 0x64, 0x4F, 0x7E, 0x28, + 0x99, 0x5D, 0xCE, 0x47, 0xC8, 0x79, 0xBA, 0x1D, 0xC2, 0x7B, 0x3B, 0x14, 0x83, 0x22, 0x88, 0xC9, 0x08, 0xCA, 0x10, 0xD7, 0x25, 0x99, 0x17, 0x6B, 0x15, 0x58, 0xC8, 0xCA, 0x1A, 0xF9, 0x51, 0x44, + 0x16, 0xA7, 0x60, 0xF3, 0xF7, 0x46, 0x21, 0x59, 0xEF, 0x95, 0x79, 0x56, 0x3E, 0xF6, 0xE3, 0xBE, 0x10, 0xB8, 0x54, 0xCD, 0xD7, 0xE8, 0x24, 0xDA, 0xE1, 0x3C, 0xEE, 0x70, 0xC8, 0x71, 0xFB, 0x6F, + 0x9B, 0xCC, 0x2C, 0x62, 0xAA, 0x41, 0x6F, 0xCF, 0x57, 0xA4, 0xDC, 0x22, 0xCA, 0xC3, 0x19, 0x8A, 0xE5, 0xAD, 0xF6, 0xE9, 0x57, 0x63, 0x5C, 0x95, 0xA8, 0xC1, 0xF8, 0xED, 0xE8, 0xF5, 0xB5, 0x14, + 0xD6, 0x81, 0xCA, 0x9B, 0xF9, 0x64, 0x43, 0x95, 0x8D, 0xDC, 0x00, 0xF0, 0x6E, 0x38, 0xD8, 0xB4, 0x95, 0x86, 0x4D, 0x5D, 0xF5, 0x6C, 0x32, 0xD2, 0x3E, 0xA9, 0x3D, 0x72, 0x1C, 0x66, 0xE6, 0x49, + 0xB2, 0x5F, 0x5B, 0x02, 0x44, 0x68, 0x4B, 0x58, 0xB1, 0x01, 0x26, 0x05, 0x55, 0x08, 0x94, 0xA2, 0x8D, 0xAD, 0x18, 0x92, 0x96, 0x6A, 0x56, 0x0E, 0x89, 0xAD, 0x7C, 0x1E, 0x4B, 0xD1, 0x76, 0x6E, + 0x63, 0x7A, 0x4F, 0xFF, 0x64, 0x2C, 0x8B, 0x14, 0xFE, 0xB7, 0xAE, 0x52, 0x41, 0xAA, 0x4C, 0x90, 0x35, 0xEC, 0x02, 0xF1, 0x78, 0x88, 0x73, 0x7A, 0xDE, 0x49, 0x0F, 0xA7, 0x92, 0xE7, 0xF7, 0x62, + 0x5E, 0x14, 0x1F, 0x95, 0x95, 0xE9, 0xF2, 0x62, 0xAD, 0xF4, 0x18, 0xAB, 0x6B, 0x31, 0xFB, 0xFE, 0x3B, 0x2E, 0x97, 0x4A, 0xB6, 0xF5, 0x2C, 0x96, 0x0B, 0x8F, 0x72, 0x9C, 0xF5, 0xE8, 0x49, 0x78, + 0x60, 0x12, 0x5C, 0xA6, 0x22, 0x99, 0x52, 0xC0, 0x71, 0xDB, 0x25, 0x8E, 0xFA, 0xDC, 0x6D, 0xBA, 0x70, 0xA1, 0x02, 0xD5, 0xB0, 0x84, 0x7B, 0x16, 0x6F, 0x21, 0x46, 0x6E, 0xBA, 0xAC, 0xF5, 0x19, + 0x9A, 0x8A, 0x9B, 0x68, 0x93, 0x3D, 0xED, 0x39, 0xB6, 0x44, 0x87, 0x13, 0x0F, 0x9C, 0x33, 0xB5, 0x1F, 0xA7, 0xBD, 0x53, 0x3A, 0x17, 0x04, 0xE4, 0x83, 0x42, 0xD6, 0xA5, 0xC0, 0xBB, 0x53, 0x97, + 0x2A, 0xD9, 0xF7, 0xE6, 0x3B, 0x53, 0x91, 0x5B, 0x3D, 0x87, 0x94, 0x9E, 0xDC, 0x6C, 0x34, 0x43, 0x38, 0xDA, 0x7B, 0x15, 0xE0, 0x7E, 0x18, 0xFF, 0xF5, 0x5B, 0xE2, 0x5D, 0x8A, 0xBB, 0x06, 0x82, + 0x2C, 0xD9, 0x5F, 0xB1, 0xA3, 0x26, 0xC7, 0xB5, 0xD0, 0xFD, 0x0C, 0x97, 0x10, 0x4B, 0xEF, 0x06, 0x7A, 0xA3, 0x00, 0x16, 0xA1, 0x33, 0x25, 0x4D, 0x02, 0xBA, 0x56, 0x52, 0x3E, 0x80, 0xE3, 0xB6, + 0xBA, 0xF9, 0x21, 0x6E, 0x0B, 0x1C, 0xEF, 0x65, 0xE2, 0xB8, 0xE4, 0x6D, 0x85, 0x69, 0x7F, 0xCA, 0xF0, 0x3E, 0xAB, 0x80, 0xC7, 0x74, 0x45, 0xCB, 0x10, 0x36, 0x6B, 0xD0, 0xB8, 0xB1, 0xC3, 0xB4, + 0xDF, 0x32, 0xED, 0xC0, 0x6C, 0xF3, 0xAF, 0x70, 0xFE, 0x29, 0x95, 0x51, 0x7E, 0x69, 0xFD, 0x2A, 0xE0, 0xBA, 0xF9, 0x58, 0x5F, 0x21, 0xF9, 0x25, 0x50, 0x4A, 0xDF, 0x8E, 0x8C, 0x91, 0xFB, 0xF2, + 0x10, 0x1C, 0xBB, 0xE7, 0x97, 0xA2, 0x66, 0x40, 0xD0, 0x8C, 0xD1, 0xF8, 0xC6, 0x41, 0x81, 0xE3, 0x82, 0x8E, 0xF2, 0xEE, 0x46, 0x20, 0x8B, 0x93, 0x12, 0x35, 0x36, 0xD0, 0x6E, 0xAB, 0x4A, 0x29, + 0xCE, 0x33, 0x4F, 0x43, 0xD4, 0x71, 0xEA, 0x15, 0x7F, 0xF7, 0xA8, 0xF3, 0x1A, 0x38, 0x7A, 0xCD, 0x03, 0xEA, 0x4B, 0x52, 0x96, 0xB4, 0x97, 0x14, 0x20, 0xE1, 0x83, 0x0E, 0xA0, 0xED, 0xE8, 0x1C, + 0x8B, 0x96, 0x54, 0x3A, 0x9F, 0xE2, 0x87, 0x63, 0xFC, 0xF5, 0x6B, 0x9A, 0xF4, 0x3F, 0x77, 0x7B, 0xCA, 0xCB, 0xEC, 0xC8, 0xAE, 0x13, 0xC3, 0xD4, 0x12, 0x66, 0x55, 0x8B, 0xEA, 0x42, 0x8E, 0xAA, + 0x10, 0xBB, 0xAC, 0xDE, 0xA9, 0x44, 0xCD, 0xA5, 0x9A, 0x1A, 0xEF, 0xB4, 0x82, 0x54, 0x81, 0x71, 0xC4, 0x2F, 0xF9, 0xC0, 0xE9, 0xD2, 0x46, 0x93, 0x5B, 0xB8, 0x0B, 0x3E, 0x34, 0x7E, 0xA1, 0xEF, + 0x9D, 0x1C, 0x51, 0xEF, 0x45, 0x5D, 0xA2, 0xDE, 0x90, 0xC8, 0x7C, 0xDB, 0xBC, 0xE1, 0x3D, 0x2F, 0xBA, 0xC8, 0xB4, 0xD4, 0x62, 0x4C, 0x36, 0xF6, 0x13, 0x49, 0x0F, 0xE5, 0xF9, 0x7E, 0x44, 0xF9, + 0x1D, 0xAE, 0x67, 0x4B, 0x09, 0xC2, 0x78, 0xA0, 0x0A, 0x95, 0x25, 0x23, 0x99, 0x3E, 0x92, 0xC6, 0x03, 0x96, 0xE9, 0x9F, 0x91, 0x67, 0x26, 0xA9, 0xB7, 0x11, 0x5F, 0xE9, 0xE2, 0x49, 0x5B, 0xD7, + 0x10, 0x2D, 0x9B, 0x61, 0x96, 0x1A, 0xEE, 0x02, 0x54, 0xB3, 0x27, 0xBF, 0xC0, 0x64, 0x46, 0x55, 0xA8, 0x5D, 0x35, 0x91, 0x8C, 0xA7, 0xD5, 0x66, 0x7E, 0xAF, 0xAE, 0x11, 0x3A, 0x12, 0x12, 0x80, + 0x50, 0x4E, 0xAC, 0x12, 0x2C, 0x04, 0x1D, 0xB2, 0x14, 0x1A, 0xA0, 0x85, 0x38, 0x15, 0xC1, 0x49, 0x96, 0x2B, 0x4D, 0x9C, 0x55, 0x99, 0xAC, 0xC7, 0x2A, 0x9E, 0x15, 0xF0, 0x06, 0xA2, 0x51, 0x96, + 0x09, 0x80, 0x0A, 0xB4, 0xEB, 0x11, 0x6D, 0x7B, 0x36, 0xBE, 0xB2, 0x59, 0x7E, 0x15, 0xA5, 0x54, 0x26, 0x3B, 0xD3, 0xB0, 0xE7, 0x8C, 0xE3, 0x8B, 0x7F, 0x60, 0x83, 0x11, 0xAB, 0x7B, 0xC3, 0xCA, + 0xF4, 0x38, 0xC5, 0x06, 0xB3, 0x23, 0x17, 0x43, 0xFE, 0x3E, 0x29, 0xF9, 0x3D, 0xF3, 0x5B, 0x34, 0x40, 0x10, 0x87, 0x04, 0x1C, 0xEE, 0x3B, 0x75, 0xAE, 0xFA, 0x0A, 0xFE, 0xAF, 0x09, 0xA6, 0xEB, + 0xF6, 0xD2, 0xFE, 0x41, 0x85, 0xBC, 0xC6, 0xB3, 0x9A, 0xED, 0x79, 0xF3, 0x38, 0x92, 0x12, 0xFD, 0xC0, 0x9F, 0xA4, 0x8A, 0x71, 0xFE, 0x6A, 0x2D, 0xE3, 0x3D, 0x40, 0xAC, 0xB6, 0xEB, 0x59, 0xE1, + 0x99, 0xB1, 0xCD, 0x76, 0x19, 0xAF, 0xE9, 0x6E, 0xD5, 0x46, 0xEE, 0xC5, 0x64, 0x39, 0x5F, 0xAC, 0x3B, 0x49, 0xA5, 0xE7, 0xAC, 0x20, 0x60, 0x68, 0x06, 0xF1, 0x91, 0x27, 0xC6, 0x38, 0x1E, 0xE3, + 0x47, 0x93, 0x6B, 0x35, 0xE3, 0x07, 0x4E, 0x23, 0xEB, 0x9E, 0xB0, 0xB0, 0x87, 0x2D, 0x67, 0x30, 0x54, 0xBF, 0x4F, 0xAB, 0x46, 0xD9, 0xC3, 0xC2, 0x75, 0x82, 0x31, 0x8A, 0x05, 0x56, 0xAA, 0x6F, + 0x5D, 0xCF, 0x79, 0x25, 0x9F, 0xF8, 0x47, 0xC0, 0xA6, 0xB5, 0x28, 0xD0, 0x49, 0xEE, 0x85, 0xE5, 0xE2, 0xD0, 0x57, 0x23, 0x49, 0x43, 0x89, 0x12, 0x51, 0x5A, 0xA9, 0x46, 0xCD, 0x2A, 0xD7, 0xF8, + 0x93, 0xA9, 0xC4, 0xD0, 0x16, 0x0A, 0x24, 0xEF, 0xAA, 0xE9, 0xE2, 0x89, 0x1A, 0xD9, 0x62, 0xB9, 0x62, 0x08, 0x0A, 0x06, 0x65, 0xFC, 0xF5, 0x4B, 0xA3, 0xE3, 0x7A, 0x83, 0x0A, 0x1E, 0x59, 0x5E, + 0xCB, 0xD0, 0xE0, 0xAC, 0x37, 0x01, 0x2E, 0x97, 0xDE, 0x3D, 0x4D, 0xAE, 0x2C, 0xA8, 0x42, 0x75, 0x25, 0x99, 0x88, 0xFC, 0x83, 0x9E, 0x0D, 0x59, 0xC1, 0x59, 0xA5, 0x18, 0x53, 0xDF, 0x57, 0xC6, + 0x22, 0xCA, 0x74, 0xCB, 0x71, 0xFD, 0xC2, 0xD5, 0x20, 0x01, 0xD4, 0xF8, 0x04, 0x73, 0x4E, 0xC0, 0x9B, 0x09, 0x0C, 0xDE, 0x83, 0x71, 0xE2, 0x6B, 0xC5, 0x7F, 0x76, 0x8C, 0x5F, 0xA0, 0x2B, 0xC6, + 0x6C, 0x6A, 0xEC, 0xB0, 0x44, 0xDA, 0x59, 0xF2, 0xCF, 0x52, 0x93, 0xB8, 0xD8, 0x6E, 0x61, 0xB8, 0x6E, 0x84, 0xEB, 0x6B, 0xA4, 0xDE, 0x6F, 0x44, 0xAC, 0xC5, 0x66, 0x2E, 0x34, 0x7B, 0xE8, 0x38, + 0xEA, 0xB6, 0xA0, 0x3B, 0x3F, 0x1E, 0xA9, 0x90, 0xA3, 0x22, 0xB0, 0xCB, 0x13, 0x09, 0x22, 0x87, 0xE7, 0xFF, 0x52, 0xF9, 0x35, 0x10, 0x45, 0x5D, 0xD2, 0xAF, 0x81, 0x1F, 0xBA, 0xE2, 0x19, 0x48, + 0x01, 0xA9, 0x0D, 0xCC, 0x2D, 0x69, 0x90, 0x59, 0x1F, 0xF9, 0x0A, 0xF8, 0x17, 0x30, 0xC7, 0xDD, 0x13, 0x91, 0xE7, 0x8D, 0x9B, 0x0E, 0x42, 0x64, 0x61, 0x55, 0xEF, 0x4C, 0x53, 0xFC, 0xF6, 0x23, + 0x9C, 0xAE, 0x7C, 0xAD, 0xEC, 0x2E, 0x8D, 0xB1, 0xFB, 0xAA, 0x91, 0x15, 0x24, 0x45, 0x4C, 0x49, 0x18, 0x4C, 0xC1, 0xA7, 0x7E, 0x57, 0x2A, 0x01, 0x67, 0xE2, 0x91, 0xC0, 0xA1, 0xEC, 0xBD, 0x9D, + 0x31, 0x70, 0x9C, 0x27, 0x7C, 0xE5, 0x41, 0xD3, 0x25, 0x56, 0x3C, 0x2E, 0xC3, 0x1E, 0x0A, 0x8B, 0x54, 0x2C, 0xAE, 0x34, 0xDC, 0x13, 0x4F, 0x66, 0x79, 0x96, 0xD8, 0x27, 0x1C, 0xA6, 0xE9, 0x0B, + 0xB8, 0x44, 0x6F, 0xB6, 0x6D, 0xBE, 0x61, 0xD2, 0x74, 0x2C, 0x38, 0xCA, 0xB4, 0x06, 0x4D, 0x2B, 0x40, 0xB6, 0x53, 0x72, 0x5B, 0x97, 0x6D, 0x37, 0xD2, 0x66, 0xAA, 0x6F, 0xA8, 0xB2, 0x99, 0x63, + 0x05, 0x8E, 0x06, 0xEF, 0xAD, 0x99, 0x07, 0x35, 0x9D, 0xE3, 0xDB, 0xC2, 0x27, 0x05, 0xFE, 0x6A, 0xB7, 0xD5, 0xFD, 0xAE, 0xB9, 0x02, 0x33, 0xEB, 0x94, 0xCB, 0x20, 0x40, 0x0B, 0x5A, 0x68, 0xC9, + 0xCE, 0xAB, 0x1A, 0x16, 0xBB, 0xBD, 0x5F, 0x1B, 0x90, 0x55, 0x6A, 0xC9, 0x38, 0x50, 0xAD, 0xFC, 0xCA, 0x90, 0x58, 0x8A, 0x1A, 0xAD, 0x3E, 0x71, 0x67, 0xEE, 0x26, 0x90, 0xEE, 0x58, 0xC1, 0xDE, + 0x36, 0xD2, 0x7B, 0xDE, 0xEA, 0xB9, 0xD8, 0x19, 0xD6, 0x9D, 0xFA, 0xF9, 0xEA, 0xE5, 0x5E, 0x1C, 0xD3, 0xA9, 0x7A, 0x5F, 0xB3, 0xFD, 0x10, 0xBB, 0xA2, 0x9D, 0x84, 0xC6, 0x9C, 0x14, 0xB2, 0x2E, + 0xDD, 0xD9, 0x91, 0xCD, 0x4E, 0xF2, 0x9F, 0xA3, 0x5D, 0xDB, 0xDE, 0xE6, 0xC9, 0xA0, 0x09, 0x6D, 0x4E, 0x7F, 0xDF, 0xCF, 0x7E, 0x28, 0x3C, 0x89, 0x91, 0x73, 0x10, 0xC8, 0x90, 0xBE, 0xEC, 0x2C, + 0x8C, 0x6C, 0xC0, 0xE6, 0xEE, 0x4A, 0xB5, 0xC2, 0x8F, 0xAA, 0xCB, 0x2E, 0x00, 0xBB, 0x93, 0xD9, 0x7E, 0x5C, 0xFB, 0xFA, 0xF8, 0xF7, 0x8B, 0xDF, 0x90, 0x2D, 0x25, 0xDF, 0xB5, 0x06, 0xA3, 0xB1, + 0x0C, 0x06, 0x48, 0xAA, 0xBB, 0xC5, 0xD4, 0xCA, 0x8B, 0x1A, 0x46, 0x6F, 0x04, 0x1B, 0xF7, 0xE1, 0x0E, 0xF5, 0x1E, 0x0D, 0x7A, 0x3F, 0xF5, 0xB1, 0x80, 0xAC, 0xBA, 0xF2, 0x36, 0xA3, 0x81, 0x51, + 0xB9, 0x56, 0xCB, 0x56, 0x35, 0x75, 0x65, 0xD7, 0x1E, 0x42, 0x60, 0xF2, 0xF6, 0x35, 0x12, 0xDC, 0xDB, 0xD3, 0xC3, 0x5E, 0x54, 0x0F, 0x87, 0x72, 0x63, 0x26, 0xAF, 0x2A, 0x3C, 0xD6, 0xEE, 0xD2, + 0xDA, 0x8E, 0x51, 0x9F, 0x9F, 0x60, 0x58, 0x1A, 0x58, 0x20, 0x13, 0xBC, 0x93, 0xBE, 0x25, 0xA0, 0x13, 0x71, 0xDC, 0x8C, 0x34, 0xBE, 0x1E, 0x88, 0x24, 0xA2, 0xD2, 0x12, 0x03, 0x39, 0xD6, 0xE2, + 0x87, 0xEC, 0x0C, 0xC4, 0x3D, 0x58, 0x6A, 0x04, 0xF8, 0x08, 0x75, 0xB3, 0x76, 0x64, 0x83, 0xB8, 0x84, 0xA9, 0x20, 0x2C, 0x1C, 0xDB, 0x4D, 0xF4, 0xC1, 0x1B, 0x1D, 0x79, 0xB1, 0xE4, 0xF2, 0xAE, + 0x88, 0x6E, 0x81, 0xA1, 0xFF, 0x7B, 0xCA, 0xC8, 0x98, 0x89, 0x53, 0x21, 0x4D, 0xAF, 0xE7, 0x79, 0xA7, 0x9D, 0xF5, 0x1A, 0x65, 0x1A, 0x51, 0x2D, 0xB2, 0x56, 0x2B, 0x7C, 0x1D, 0x46, 0x71, 0xD5, + 0x2C, 0x51, 0x70, 0x81, 0xD5, 0x3A, 0x79, 0x22, 0x70, 0xB1, 0xC3, 0x05, 0x51, 0x5F, 0xB7, 0xB6, 0xC4, 0x61, 0xBD, 0x4C, 0xD0, 0xD7, 0xC3, 0x17, 0x5B, 0x14, 0x6F, 0xE9, 0x62, 0xA4, 0xC9, 0xA9, + 0x08, 0x1E, 0x39, 0x49, 0x60, 0x68, 0x9B, 0xA9, 0xBC, 0xC6, 0xCA, 0xD5, 0xEA, 0xED, 0xF8, 0x1E, 0x34, 0x53, 0x61, 0x64, 0x6E, 0x9E, 0xAF, 0xB8, 0xBA, 0xEC, 0xF1, 0xFC, 0x01, 0x12, 0x1C, 0x29, + 0x3D, 0x58, 0x68, 0x7D, 0x7E, 0x81, 0xA4, 0xA8, 0xAE, 0xC9, 0x0F, 0x16, 0x1D, 0x73, 0x87, 0x97, 0xAC, 0xAE, 0xBE, 0xC1, 0x18, 0x19, 0x58, 0x67, 0x9D, 0xA1, 0xA7, 0xAA, 0xB0, 0xEB, 0xEE, 0xF0, + 0xF1, 0xFF, 0x18, 0x32, 0x3C, 0x47, 0x5D, 0x6A, 0x72, 0x7F, 0x80, 0x82, 0x93, 0xAD, 0xBD, 0xCC, 0xDF, 0xE6, 0xEC, 0xF0, 0xFD, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0F, 0x1C, 0x2A, 0x34, 0x42, 0x55, 0x80, 0x16, + 0x15, 0x00, 0x78, 0x78, 0x2C, 0x25, 0x10, 0x0C, 0x02, 0x01, 0x82, 0x08, 0xD8, 0x80, 0x82, 0x02, 0xC4, 0x02, 0x01, 0x20, 0x27, 0x80, 0x84, 0x4A, 0x00, 0x12, 0x82, 0x02, 0x00, 0x50, 0x64, 0x4A, + 0xB2, 0xB4, 0x16, 0xBF, 0x7C, 0x04 }, + }, + { + .name = "Dilithium Round 2, Level 4 (6-5) KAT 0", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_65, .rho_len = 32, .rho = { 0x7C, 0x99, 0x35, 0xA0, 0xB0, 0x76, 0x94, 0xAA, 0x0C, 0x6D, 0x10, 0xE4, 0xDB, 0x6B, 0x1A, 0xDD, 0x2F, 0xD8, 0x1A, 0x25, 0xCC, 0xB1, 0x48, 0x03, 0x2D, 0xCD, 0x73, 0x99, 0x36, 0x73, 0x7F, 0x2D }, .seed_len = 32, @@ -250,6 +619,8 @@ 0x97, 0x6A, 0xBC, 0xC9, 0x5C, 0x14, 0xA8, 0xEF, 0xE6, 0x0A, 0x2C, 0x1A, 0xF0, 0xAB, 0xBE, 0x6B, 0xF7, 0x89, 0xD4, 0xF6, 0x97, 0x38, 0x09, 0x2A, 0xE3, 0xE6, 0x2A, 0xF1, 0x77, 0x3E, 0xD6, 0xA4, 0x2F, 0x1A, 0xAA, 0xBC, 0xFB, 0x98, 0x73, 0x1C, 0xE2, 0x70, 0x1F, 0x42, 0xE4, 0xBA, 0x9E, 0x12, 0x8B, 0x67, 0x26, 0x1C, 0x59, 0x8D, 0x31, 0x89, 0xD0, 0x60, 0x24, 0xF0, 0x1E, 0x25, 0x35, 0x4D, 0x60, 0x32, 0x7F, 0xB6, 0x57, 0x0B, 0xF7, 0xE1, 0x63, 0xFA, 0x04, 0x32, 0x4B, 0x32, 0xE7, 0xEB, 0xF8, 0xB7, 0x8A, 0xC2, 0xEC, 0xFA, 0x3D, 0x36, 0xB1, 0x3A, 0x59, 0xA3, 0xA7, 0x27, 0x02, 0x9B }, + .pkcs8_len = 0, + .spki_len = 0, .msg_len = 33, .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, 0xC8 }, @@ -363,8 +734,9 @@ 0xB2, 0xB4, 0x16, 0xBF, 0x7C, 0x04 }, }, { - .name = "Dilithium 6-5 KAT 1", + .name = "Dilithium Round 2, Level 4 (6-5) KAT 1", .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_65, .rho_len = 32, .rho = { 0xBC, 0x96, 0x2D, 0x97, 0x8F, 0x38, 0x88, 0x10, 0x85, 0xC1, 0xB8, 0x13, 0xBC, 0x90, 0xEE, 0xE4, 0x4A, 0xD9, 0xE7, 0x65, 0x16, 0x81, 0xC2, 0x0B, 0xA4, 0x64, 0x02, 0xF5, 0x57, 0xC4, 0x54, 0xDE }, .seed_len = 32, @@ -547,6 +919,8 @@ 0x6B, 0x50, 0x20, 0x56, 0x35, 0xCD, 0x16, 0xA5, 0xB4, 0xC2, 0x58, 0xA9, 0xC7, 0x33, 0x15, 0x11, 0x93, 0xE4, 0x1C, 0x73, 0xEA, 0xAD, 0xC8, 0x86, 0x41, 0x76, 0x42, 0x73, 0xDF, 0x00, 0xD6, 0x6F, 0xE3, 0x84, 0x78, 0x3B, 0x95, 0xD5, 0x30, 0xC6, 0x90, 0x0B, 0x4A, 0x93, 0x84, 0x1D, 0x40, 0x54, 0x3E, 0x56, 0x37, 0x40, 0x75, 0x1A, 0xDE, 0x91, 0x63, 0xBA, 0x9A, 0x28, 0xAE, 0x8C, 0x95, 0xCF, 0x15, 0x65, 0x34, 0xF9, 0x78, 0x1F, 0x35, 0xE7, 0x5F, 0x1C, 0x0E, 0xD8, 0x78, 0x98, 0xC0, 0xB5, 0x9B, 0x82, 0x13, 0x68, 0x86, 0xA2, 0x20, 0xC3, 0x4F, 0xD4, 0xDD, 0xC3, 0x96, 0x7C, 0xEF, 0x7D }, + .pkcs8_len = 0, + .spki_len = 0, .msg_len = 891, .msg = { 0x30, 0xD6, 0x1C, 0x6F, 0xBD, 0x64, 0x11, 0x3F, 0xCE, 0xD8, 0xC5, 0x20, 0x50, 0x26, 0xEB, 0xAC, 0x0D, 0x9F, 0x35, 0x22, 0x18, 0x26, 0x17, 0xCB, 0x00, 0xB6, 0xE7, 0x0C, 0x8D, 0xA6, 0x2E, 0xCC, 0x1B, 0xBC, 0x8E, 0x1F, 0xDA, 0xF1, 0x7C, 0xC6, 0x1D, 0xD0, 0x1C, 0xE8, 0x5A, 0x90, 0x72, 0xCC, 0x1D, 0x9D, 0x34, 0xFD, 0xAD, 0xBA, 0x5B, 0x93, 0xE0, 0xAA, 0xB4, 0xC9, 0xC4, 0xC9, 0xE2, 0x6D, @@ -685,8 +1059,9 @@ 0x94, 0x55, 0x2B, 0xE6, 0x37, 0x0B }, }, { - .name = "Dilithium 6-5 KAT 2", + .name = "Dilithium Round 2, Level 4 (6-5) KAT 2", .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_65, .rho_len = 32, .rho = { 0xDF, 0x48, 0x53, 0xF4, 0x82, 0xCC, 0x1D, 0x0B, 0x3A, 0x2D, 0x71, 0xE9, 0xEA, 0xCA, 0x06, 0x4E, 0x57, 0xC5, 0xD1, 0x00, 0xDF, 0x79, 0xBD, 0x00, 0x4B, 0xA8, 0x1B, 0x43, 0xEA, 0xCE, 0xC4, 0x01 }, .seed_len = 32, @@ -869,6 +1244,8 @@ 0x22, 0x1E, 0x28, 0xD0, 0x85, 0x75, 0xB0, 0x42, 0x8F, 0x66, 0x63, 0x9F, 0x76, 0x06, 0xB0, 0x78, 0x25, 0x05, 0x5A, 0xBA, 0xE8, 0x17, 0xCD, 0x67, 0xAF, 0x4E, 0xD7, 0x59, 0x57, 0x3D, 0xF0, 0x51, 0x02, 0x88, 0x79, 0xA1, 0x73, 0x0E, 0x89, 0x87, 0x55, 0x69, 0xD7, 0xFA, 0x12, 0x0F, 0x81, 0x80, 0xB9, 0x04, 0x95, 0x82, 0x93, 0x42, 0x8A, 0xF8, 0x9B, 0x9C, 0x96, 0x15, 0x2C, 0x40, 0x87, 0x81, 0x2F, 0xDE, 0x74, 0x4F, 0x42, 0x41, 0x70, 0x5C, 0x85, 0x8A, 0x71, 0xB0, 0x0E, 0x66, 0xDA, 0xD4, 0x0F, 0xCF, 0x62, 0xB2, 0x23, 0x70, 0xFF, 0x6B, 0xAE, 0xA8, 0xF5, 0x18, 0x70, 0x78, 0x17, 0x75 }, + .pkcs8_len = 0, + .spki_len = 0, .msg_len = 2442, .msg = { 0xAC, 0xB4, 0x14, 0xEB, 0x55, 0xAE, 0x5E, 0x49, 0x10, 0x7B, 0xD0, 0xAC, 0x59, 0x75, 0x54, 0x4F, 0x83, 0x10, 0x4F, 0x72, 0x64, 0x49, 0x5A, 0xE0, 0xBF, 0x0A, 0x6D, 0x95, 0x94, 0xC4, 0x22, 0xC1, 0x6B, 0x99, 0x46, 0x9E, 0xCC, 0xDF, 0xE8, 0xB8, 0x00, 0x08, 0x75, 0xB4, 0x69, 0x30, 0x98, 0x91, 0xEA, 0x42, 0x58, 0x6A, 0x61, 0x5D, 0x14, 0x6D, 0xE6, 0x4F, 0xE5, 0x92, 0x77, 0xA6, 0x16, 0x31, @@ -1056,8 +1433,9 @@ 0xA5, 0x26, 0x63, 0x08, 0xD2, 0x06 }, }, { - .name = "Dilithium 6-5 KAT 3", + .name = "Dilithium Round 2, Level 4 (6-5) KAT 3", .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_65, .rho_len = 32, .rho = { 0x69, 0x04, 0x82, 0xBF, 0xF6, 0xC1, 0xD0, 0xBA, 0x6C, 0x07, 0x1D, 0xD3, 0x95, 0xAD, 0xF6, 0x9E, 0x55, 0xE1, 0xBF, 0xC4, 0xE0, 0x99, 0x2A, 0x86, 0x50, 0xFF, 0xB5, 0xE6, 0x0A, 0x02, 0xB1, 0x72 }, .seed_len = 32, @@ -1240,6 +1618,8 @@ 0x5F, 0x41, 0xFF, 0xFC, 0xD8, 0xBA, 0x32, 0x59, 0x43, 0x59, 0x53, 0x98, 0xB2, 0xD9, 0x39, 0xC8, 0xA4, 0xC9, 0x0B, 0x1D, 0x58, 0x4C, 0x66, 0x9F, 0x0F, 0xFA, 0xCD, 0x43, 0x41, 0xE0, 0x35, 0x58, 0x70, 0x07, 0x15, 0xC6, 0x1C, 0x3C, 0x64, 0x0D, 0x42, 0x5B, 0x67, 0xEB, 0x0D, 0xAA, 0xBF, 0x5E, 0xD3, 0x09, 0x20, 0x5F, 0xB0, 0x9A, 0x0C, 0x6B, 0x3D, 0xDD, 0xBB, 0x5F, 0x28, 0x8E, 0x57, 0x3B, 0x46, 0x1A, 0x58, 0xF5, 0xEF, 0x5D, 0x43, 0x50, 0x13, 0x63, 0xD8, 0xB1, 0xA7, 0x79, 0xDC, 0x5E, 0x27, 0xDE, 0xAC, 0xDF, 0xCD, 0xCD, 0x0A, 0x9C, 0x20, 0x24, 0xAE, 0x48, 0x1C, 0xD9, 0x81, 0xD5 }, + .pkcs8_len = 0, + .spki_len = 0, .msg_len = 3300, .msg = { 0xD2, 0x1A, 0x6B, 0xB3, 0xA2, 0x35, 0x68, 0x05, 0xE6, 0x78, 0x67, 0x3C, 0x45, 0xFB, 0x05, 0x5F, 0xC5, 0x26, 0x6E, 0x3F, 0x69, 0x2A, 0xF9, 0x93, 0x5A, 0xEA, 0x30, 0x7F, 0x14, 0xA5, 0xC4, 0x1B, 0x97, 0x99, 0x66, 0xA5, 0xDF, 0xE4, 0x2E, 0xBF, 0xED, 0x14, 0x87, 0xE4, 0x82, 0x2B, 0x74, 0xAB, 0x5A, 0xF2, 0x89, 0x95, 0xE0, 0x85, 0xEC, 0x80, 0x07, 0xEC, 0xA4, 0x97, 0x7C, 0x63, 0xEE, 0x52, @@ -1453,6 +1833,4375 @@ 0x00, 0x02, 0x16, 0xA0, 0x74, 0x00, 0x30, 0xB2, 0x40, 0x10, 0x95, 0x00, 0x0C, 0x00, 0x23, 0x42, 0x13, 0x20, 0x06, 0x06, 0x9C, 0x00, 0x00, 0x25, 0x04, 0x80, 0x09, 0xE2, 0x28, 0x84, 0xA2, 0x32, 0x13, 0x7D, 0xE1, 0xCE, 0xBE, 0x04 }, }, + { + .name = "Dilithium Round 2, Level 5 (8-7) KAT 0 (PKCS#8/SPKI)", + .version = 0, + .keyform = 0, + .rho_len = 0, + .seed_len = 0, + .tr_len = 0, + .s1_len = 0, + .s2_len = 0, + .t0_len = 0, + .t1_len = 0, + .pkcs8_len = 7508, + .pkcs8 = { + 0x30, 0x82, 0x1D, 0x50, 0x02, 0x01, 0x00, 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0B, 0x01, 0x08, 0x07, 0x05, 0x00, 0x04, 0x82, 0x1D, 0x38, 0x30, 0x82, 0x1D, 0x34, + 0x02, 0x01, 0x00, 0x03, 0x21, 0x00, 0x7C, 0x99, 0x35, 0xA0, 0xB0, 0x76, 0x94, 0xAA, 0x0C, 0x6D, 0x10, 0xE4, 0xDB, 0x6B, 0x1A, 0xDD, 0x2F, 0xD8, 0x1A, 0x25, 0xCC, 0xB1, 0x48, 0x03, 0x2D, 0xCD, + 0x73, 0x99, 0x36, 0x73, 0x7F, 0x2D, 0x03, 0x21, 0x00, 0x3E, 0x78, 0x4C, 0xCB, 0x7E, 0xBC, 0xDC, 0xFD, 0x45, 0x54, 0x2B, 0x7F, 0x6A, 0xF7, 0x78, 0x74, 0x2E, 0x0F, 0x44, 0x79, 0x17, 0x50, 0x84, + 0xAA, 0x48, 0x8B, 0x3B, 0x74, 0x34, 0x06, 0x78, 0xAA, 0x03, 0x31, 0x00, 0x89, 0xDB, 0xBF, 0xC3, 0x69, 0x33, 0x5D, 0x8F, 0x70, 0xE7, 0xBC, 0xB4, 0xD1, 0x66, 0xD4, 0xBD, 0xD0, 0xD8, 0x36, 0xE4, + 0x5D, 0xE9, 0x37, 0x92, 0xED, 0xC4, 0x26, 0x10, 0x6F, 0xBF, 0x5A, 0xF2, 0x7C, 0x68, 0xA9, 0x50, 0xB4, 0xA1, 0xA6, 0x42, 0x28, 0x01, 0xC6, 0xF2, 0xAC, 0xC3, 0xA9, 0xFA, 0x03, 0x82, 0x02, 0xA1, + 0x00, 0x91, 0xB4, 0x2D, 0xA1, 0x38, 0x24, 0x08, 0x19, 0x24, 0x1A, 0x30, 0x4D, 0x40, 0xA8, 0x6C, 0xD8, 0x04, 0x6A, 0x03, 0x28, 0x04, 0x41, 0x38, 0x22, 0x22, 0x39, 0x0A, 0xE2, 0x80, 0x0D, 0x12, + 0x49, 0x91, 0x24, 0xB4, 0x50, 0x93, 0x46, 0x89, 0xD1, 0x30, 0x4C, 0x04, 0x20, 0x24, 0x20, 0x20, 0x31, 0x59, 0x92, 0x41, 0xC3, 0x26, 0x61, 0x14, 0x47, 0x32, 0xDB, 0x12, 0x69, 0x63, 0x46, 0x01, + 0x10, 0x93, 0x91, 0x10, 0x39, 0x81, 0x5B, 0x26, 0x71, 0x40, 0xB0, 0x01, 0x03, 0x41, 0x48, 0x04, 0x19, 0x09, 0x13, 0xB4, 0x91, 0x0C, 0x46, 0x08, 0xD4, 0x08, 0x09, 0x0C, 0x99, 0x04, 0x00, 0x35, + 0x61, 0x13, 0x14, 0x4C, 0x19, 0x41, 0x28, 0x1C, 0x16, 0x80, 0x88, 0xA0, 0x29, 0x1A, 0x30, 0x02, 0x10, 0x80, 0x4C, 0x13, 0x43, 0x25, 0x04, 0x08, 0x81, 0x20, 0x43, 0x70, 0x14, 0x11, 0x6A, 0x99, + 0x00, 0x40, 0x48, 0x82, 0x31, 0x12, 0x42, 0x20, 0x48, 0x06, 0x0D, 0xE2, 0xA2, 0x0C, 0x82, 0xB0, 0x28, 0xE2, 0x36, 0x10, 0x49, 0x16, 0x84, 0xD8, 0x04, 0x4C, 0x51, 0xB8, 0x68, 0xC2, 0x84, 0x90, + 0x9B, 0x10, 0x31, 0x21, 0x49, 0x32, 0x94, 0x20, 0x0D, 0x04, 0x41, 0x24, 0xCB, 0xA4, 0x6D, 0x1A, 0x82, 0x61, 0x08, 0x40, 0x8E, 0xA4, 0x00, 0x44, 0x93, 0x92, 0x91, 0x8C, 0x30, 0x62, 0x60, 0xB2, + 0x90, 0x58, 0x40, 0x62, 0x11, 0x97, 0x31, 0x21, 0x11, 0x81, 0x0C, 0x28, 0x88, 0x09, 0x07, 0x42, 0x88, 0x40, 0x6C, 0xC0, 0x96, 0x28, 0x81, 0x28, 0x8A, 0xC0, 0x12, 0x0C, 0x93, 0x48, 0x4C, 0x89, + 0x82, 0x25, 0xD8, 0x00, 0x22, 0x24, 0x45, 0x41, 0x1B, 0x95, 0x2C, 0xA0, 0x92, 0x61, 0x84, 0xA2, 0x70, 0x59, 0x86, 0x10, 0x0B, 0x87, 0x08, 0x10, 0x98, 0x61, 0xD3, 0x40, 0x0D, 0x40, 0xB0, 0x8D, + 0x09, 0x05, 0x71, 0x60, 0x84, 0x70, 0x18, 0x80, 0x61, 0x1A, 0x16, 0x2E, 0x63, 0x32, 0x06, 0x80, 0x80, 0x88, 0x50, 0xC6, 0x8C, 0x00, 0x10, 0x24, 0xC1, 0x00, 0x26, 0x94, 0x90, 0x48, 0x44, 0xB6, + 0x29, 0x1A, 0x35, 0x48, 0xD3, 0xB0, 0x91, 0x21, 0xA4, 0x08, 0x11, 0x34, 0x32, 0x03, 0x01, 0x05, 0x21, 0x32, 0x46, 0x1B, 0x31, 0x31, 0x1B, 0x86, 0x0C, 0x1A, 0x28, 0x0D, 0xD1, 0x08, 0x28, 0x8B, + 0xA8, 0x0D, 0x98, 0x90, 0x05, 0xD0, 0xA8, 0x29, 0x83, 0x48, 0x71, 0x03, 0x33, 0x80, 0x24, 0x90, 0x68, 0xD1, 0xA0, 0x2C, 0x23, 0x10, 0x4D, 0x12, 0x95, 0x11, 0xE4, 0x14, 0x21, 0x14, 0x39, 0x4E, + 0x12, 0x01, 0x70, 0x0C, 0x25, 0x71, 0x24, 0x83, 0x89, 0x54, 0x30, 0x06, 0x11, 0x90, 0x45, 0x12, 0x03, 0x04, 0x59, 0xB0, 0x4C, 0x20, 0x36, 0x8A, 0x19, 0x30, 0x72, 0x98, 0x94, 0x4C, 0x14, 0x81, + 0x40, 0xA2, 0xC6, 0x84, 0xCB, 0xA2, 0x48, 0x0C, 0xC1, 0x2D, 0x8A, 0xC4, 0x05, 0x42, 0x94, 0x45, 0x5B, 0xB4, 0x08, 0xDB, 0x18, 0x24, 0x88, 0x20, 0x90, 0x1B, 0xC3, 0x50, 0xA1, 0x96, 0x4D, 0x0B, + 0x31, 0x6D, 0x93, 0x26, 0x46, 0x00, 0x35, 0x52, 0x01, 0x13, 0x42, 0xDA, 0x46, 0x6A, 0x1A, 0x34, 0x01, 0x40, 0x92, 0x41, 0xC0, 0x08, 0x66, 0xE3, 0x94, 0x01, 0x63, 0x28, 0x69, 0x0C, 0x25, 0x31, + 0x0B, 0x21, 0x24, 0x43, 0xA2, 0x30, 0xD3, 0x22, 0x44, 0xCB, 0x36, 0x71, 0x02, 0x02, 0x42, 0x1A, 0xC1, 0x2C, 0x20, 0x23, 0x80, 0x8B, 0xA8, 0x85, 0x88, 0x08, 0x4A, 0x94, 0x10, 0x48, 0x18, 0x81, + 0x29, 0xE2, 0xB4, 0x4C, 0x89, 0x88, 0x51, 0xC9, 0x06, 0x09, 0xD3, 0x96, 0x71, 0x54, 0xB0, 0x91, 0x53, 0x86, 0x04, 0x53, 0xC4, 0x44, 0x81, 0x98, 0x11, 0x88, 0x20, 0x04, 0xA0, 0x16, 0x0A, 0x49, + 0xA0, 0x10, 0x1A, 0x17, 0x44, 0x21, 0x26, 0x66, 0xE0, 0xC0, 0x09, 0x59, 0x90, 0x8C, 0x93, 0x10, 0x49, 0x00, 0x85, 0x65, 0x4C, 0xC6, 0x0D, 0x00, 0x18, 0x30, 0x1B, 0x12, 0x6E, 0x10, 0x02, 0x45, + 0xA2, 0x12, 0x49, 0x22, 0xC8, 0x20, 0x03, 0xC5, 0x48, 0x12, 0x04, 0x52, 0xA1, 0x88, 0x25, 0x40, 0xB2, 0x4D, 0x4B, 0x38, 0x28, 0x23, 0xB2, 0x64, 0xC2, 0x38, 0x90, 0x09, 0x46, 0x92, 0x0C, 0x90, + 0x0D, 0x04, 0x06, 0x0C, 0x4C, 0x16, 0x2D, 0x08, 0x10, 0x49, 0x20, 0x47, 0x65, 0x50, 0x28, 0x29, 0x1A, 0x88, 0x80, 0x40, 0x30, 0x6D, 0x88, 0x36, 0x70, 0x63, 0x98, 0x71, 0x99, 0x96, 0x2C, 0x1B, + 0x91, 0x61, 0x61, 0x40, 0x06, 0x13, 0x35, 0x04, 0x09, 0x08, 0x8E, 0x54, 0xB8, 0x44, 0x81, 0x30, 0x08, 0xC8, 0x10, 0x2C, 0x5A, 0xB0, 0x04, 0x42, 0x46, 0x61, 0x20, 0x03, 0x88, 0x91, 0xA0, 0x91, + 0x81, 0x10, 0x4D, 0x12, 0xB7, 0x81, 0x20, 0x42, 0x02, 0x54, 0x94, 0x24, 0x59, 0xC4, 0x25, 0x8C, 0x44, 0x70, 0xE3, 0x32, 0x8E, 0x9A, 0x02, 0x60, 0xE4, 0xA6, 0x21, 0x4A, 0xB2, 0x85, 0x93, 0x36, + 0x20, 0x03, 0x82, 0x03, 0x01, 0x00, 0x01, 0x05, 0x32, 0x11, 0x44, 0x66, 0xE2, 0x06, 0x40, 0x14, 0x49, 0x6C, 0x0B, 0x86, 0x80, 0x02, 0x47, 0x26, 0xD2, 0xB2, 0x25, 0x58, 0x48, 0x0E, 0x58, 0x44, + 0x11, 0xD1, 0x44, 0x50, 0x51, 0xB8, 0x81, 0xC4, 0xA0, 0x48, 0x10, 0xC9, 0x50, 0x08, 0x98, 0x88, 0xD8, 0x28, 0x2A, 0x52, 0xC0, 0x4D, 0xD1, 0x38, 0x12, 0xD8, 0x46, 0x89, 0x00, 0x94, 0x00, 0xDA, + 0xC4, 0x45, 0x9B, 0x44, 0x6E, 0x0B, 0x44, 0x0C, 0xC0, 0xC0, 0x01, 0x20, 0xC1, 0x0C, 0xC0, 0x04, 0x4C, 0x08, 0x24, 0x21, 0x23, 0xC7, 0x65, 0x03, 0xA0, 0x80, 0x91, 0xC2, 0x50, 0x21, 0x10, 0x31, + 0x99, 0x36, 0x00, 0x64, 0x28, 0x70, 0x81, 0x38, 0x05, 0x4A, 0x18, 0x80, 0x1C, 0x89, 0x24, 0x08, 0x95, 0x49, 0x24, 0x39, 0x40, 0x24, 0x15, 0x22, 0xD9, 0x32, 0x90, 0x23, 0x24, 0x71, 0xC4, 0x46, + 0x50, 0xCB, 0x86, 0x65, 0xE4, 0x94, 0x8C, 0x42, 0x04, 0x82, 0x8A, 0x86, 0x71, 0x13, 0xA3, 0x00, 0xDB, 0x44, 0x04, 0x23, 0x82, 0x10, 0x23, 0x46, 0x26, 0x0B, 0x08, 0x08, 0x60, 0x16, 0x11, 0xA4, + 0xB6, 0x24, 0xE1, 0x32, 0x69, 0x04, 0x17, 0x86, 0xE3, 0x84, 0x2C, 0x9C, 0x32, 0x41, 0x92, 0xC8, 0x61, 0x5A, 0x32, 0x26, 0x24, 0xC3, 0x29, 0x5A, 0xC8, 0x05, 0x0A, 0x06, 0x8E, 0xE1, 0x16, 0x20, + 0x99, 0x94, 0x61, 0x19, 0xA2, 0x0C, 0x1B, 0x05, 0x2E, 0x1B, 0x44, 0x64, 0x9A, 0x00, 0x84, 0x8C, 0x18, 0x52, 0x84, 0xB4, 0x60, 0x82, 0x20, 0x08, 0x42, 0x48, 0x09, 0x84, 0x08, 0x46, 0x11, 0x00, + 0x46, 0x13, 0x43, 0x01, 0xE1, 0x06, 0x91, 0x1B, 0x44, 0x8E, 0x01, 0x94, 0x64, 0x4A, 0x12, 0x09, 0x98, 0x38, 0x0E, 0xE4, 0x06, 0x25, 0x24, 0x13, 0x68, 0x13, 0x21, 0x06, 0x04, 0xB9, 0x40, 0x54, + 0x24, 0x25, 0x14, 0x88, 0x69, 0x82, 0x38, 0x01, 0xA4, 0x28, 0x72, 0x50, 0x86, 0x61, 0x23, 0xB1, 0x88, 0xA2, 0x90, 0x08, 0x1C, 0x95, 0x30, 0x1C, 0x40, 0x82, 0x49, 0xC8, 0x64, 0xCA, 0x04, 0x40, + 0x44, 0x98, 0x21, 0x0B, 0x24, 0x61, 0x1C, 0xA0, 0x4C, 0x09, 0xA4, 0x21, 0xC9, 0x08, 0x8A, 0x22, 0x13, 0x41, 0x80, 0xC8, 0x89, 0x23, 0xB1, 0x64, 0x1C, 0x11, 0x49, 0x40, 0xA2, 0x29, 0x61, 0xC8, + 0x8C, 0x8B, 0x96, 0x91, 0x83, 0x02, 0x42, 0xE1, 0xB6, 0x85, 0x51, 0x86, 0x4C, 0x04, 0x43, 0x91, 0x4B, 0xB8, 0x69, 0x50, 0x24, 0x81, 0xC8, 0x04, 0x2E, 0x1B, 0xB9, 0x31, 0x93, 0x24, 0x00, 0x23, + 0x86, 0x81, 0xC2, 0xB8, 0x61, 0x09, 0x00, 0x62, 0x14, 0x99, 0x41, 0x19, 0x37, 0x6E, 0x1C, 0x16, 0x30, 0x0A, 0x27, 0x45, 0x51, 0x10, 0x0D, 0x1C, 0x33, 0x4A, 0x10, 0x40, 0x80, 0xA0, 0x34, 0x62, + 0xD8, 0x44, 0x4A, 0x01, 0x06, 0x45, 0x23, 0x83, 0x8C, 0x24, 0xA4, 0x85, 0x01, 0x04, 0x0C, 0x09, 0x03, 0x32, 0xDB, 0x90, 0x09, 0x4A, 0x14, 0x42, 0x01, 0x08, 0x21, 0x22, 0x08, 0x66, 0x8B, 0x28, + 0x70, 0x24, 0x38, 0x31, 0x0C, 0x46, 0x69, 0x43, 0x44, 0x69, 0x9A, 0x34, 0x4D, 0x82, 0xC8, 0x40, 0x42, 0x42, 0x01, 0x23, 0xC7, 0x29, 0x91, 0x32, 0x72, 0x1B, 0x36, 0x4C, 0x1B, 0x33, 0x05, 0x13, + 0x35, 0x61, 0x14, 0x02, 0x46, 0x08, 0x03, 0x65, 0x21, 0x87, 0x20, 0x09, 0x03, 0x91, 0xC1, 0xC4, 0x25, 0xE2, 0xA6, 0x4C, 0x81, 0x14, 0x48, 0x20, 0x25, 0x4D, 0x03, 0x19, 0x69, 0xA3, 0x00, 0x69, + 0x54, 0xA8, 0x30, 0x9C, 0x86, 0x05, 0x9C, 0x36, 0x82, 0x03, 0x37, 0x0C, 0x0A, 0x15, 0x50, 0x9C, 0xC0, 0x91, 0x04, 0xB6, 0x91, 0x0C, 0x11, 0x80, 0x09, 0xB5, 0x70, 0x63, 0x20, 0x92, 0x44, 0x22, + 0x71, 0xC1, 0x48, 0x44, 0x98, 0xC4, 0x6D, 0x64, 0xA6, 0x89, 0x0A, 0xA9, 0x40, 0x04, 0xB8, 0x50, 0x04, 0x34, 0x8C, 0xE2, 0xC4, 0x80, 0x02, 0x00, 0x12, 0xA3, 0x36, 0x46, 0xD2, 0x00, 0x01, 0x1C, + 0x45, 0x46, 0x22, 0x33, 0x6D, 0x81, 0x92, 0x01, 0x08, 0x12, 0x86, 0x9C, 0x04, 0x51, 0xA3, 0x98, 0x30, 0x48, 0x10, 0x91, 0x19, 0xA0, 0x44, 0xC3, 0x04, 0x8D, 0x42, 0x90, 0x40, 0x43, 0x80, 0x44, + 0xA4, 0x46, 0x71, 0x0B, 0xA2, 0x60, 0x52, 0x18, 0x6D, 0x0B, 0xB6, 0x85, 0x1B, 0xB2, 0x0C, 0x94, 0x12, 0x09, 0x04, 0xB6, 0x41, 0x18, 0xA8, 0x84, 0x10, 0x00, 0x22, 0x53, 0x42, 0x69, 0xC3, 0xA8, + 0x81, 0x00, 0x25, 0x32, 0x81, 0x16, 0x28, 0x81, 0x44, 0x2D, 0xD4, 0xB4, 0x4D, 0x08, 0xC8, 0x45, 0x5A, 0x04, 0x01, 0xC1, 0x90, 0x50, 0x22, 0x14, 0x82, 0x63, 0xC6, 0x6D, 0x04, 0x22, 0x72, 0x1C, + 0xB9, 0x44, 0x9B, 0x46, 0x0D, 0xC2, 0x14, 0x22, 0x91, 0xB0, 0x44, 0x21, 0x89, 0x68, 0xC4, 0x96, 0x08, 0x0A, 0xB9, 0x8C, 0x22, 0xB9, 0x40, 0xE2, 0x26, 0x50, 0x8C, 0x88, 0x25, 0xCB, 0xB8, 0x04, + 0x54, 0x16, 0x25, 0x63, 0x34, 0x0C, 0x24, 0xB0, 0x29, 0xA3, 0x44, 0x20, 0x43, 0x46, 0x40, 0x9C, 0x02, 0x48, 0x5A, 0xC8, 0x2C, 0x00, 0x05, 0x31, 0x09, 0x18, 0x00, 0xDB, 0x46, 0x51, 0xD2, 0xB6, + 0x2C, 0x44, 0x40, 0x88, 0x9A, 0x96, 0x24, 0x12, 0xA5, 0x90, 0x04, 0x39, 0x86, 0x10, 0x80, 0x2D, 0x10, 0x99, 0x21, 0x60, 0x06, 0x66, 0x21, 0x89, 0x4C, 0x91, 0x04, 0x60, 0x23, 0xB9, 0x01, 0x12, + 0x11, 0x48, 0x12, 0x29, 0x51, 0xA1, 0x06, 0x45, 0x44, 0x22, 0x12, 0x03, 0x27, 0x8E, 0x23, 0x94, 0x84, 0x0C, 0x29, 0x06, 0x94, 0x86, 0x50, 0xE0, 0x48, 0x10, 0x24, 0x26, 0x40, 0x61, 0x04, 0x66, + 0x9C, 0xB2, 0x84, 0x54, 0xC2, 0x2C, 0x03, 0x82, 0x0E, 0x01, 0x00, 0xD6, 0xD4, 0x27, 0x24, 0xCA, 0xFD, 0xF2, 0x81, 0xB9, 0xCA, 0xDC, 0x58, 0x04, 0x84, 0x83, 0x95, 0x49, 0x25, 0x4C, 0x9B, 0xE0, + 0xA1, 0xF9, 0xAA, 0x9D, 0x76, 0xE6, 0x54, 0x63, 0xCD, 0x83, 0x14, 0x20, 0x65, 0xE7, 0xF7, 0x47, 0xBD, 0x27, 0x4C, 0xF3, 0x7E, 0x85, 0x70, 0xE0, 0xE6, 0x3A, 0xDB, 0xF8, 0x5F, 0x31, 0x79, 0x14, + 0x75, 0xFF, 0x1A, 0x2F, 0x50, 0x5B, 0x53, 0x24, 0x77, 0x2C, 0xB0, 0xEB, 0x21, 0x9E, 0x2C, 0x28, 0xC4, 0xEF, 0xBC, 0x31, 0xE7, 0x13, 0xDF, 0x18, 0x77, 0x25, 0xB7, 0xBD, 0xE2, 0x90, 0xE6, 0x08, + 0x98, 0x5B, 0x7D, 0x8A, 0x71, 0x14, 0x42, 0xD4, 0x03, 0xD2, 0x56, 0xF5, 0x35, 0xA4, 0x27, 0x1F, 0x6C, 0xC6, 0x5F, 0x91, 0xF1, 0xA7, 0x3F, 0x3B, 0x33, 0x94, 0x83, 0x3D, 0xF0, 0x12, 0x79, 0xDC, + 0x71, 0xFB, 0x60, 0xBD, 0x14, 0x13, 0xBF, 0x23, 0xBA, 0x3A, 0x20, 0xC7, 0x15, 0xC1, 0x30, 0xDA, 0x19, 0x2D, 0x05, 0x1F, 0xF6, 0xEA, 0x7E, 0xDD, 0xBB, 0x81, 0xDB, 0xC4, 0xBE, 0xBA, 0xF6, 0x71, + 0x41, 0x23, 0x6E, 0x5D, 0x9E, 0x09, 0x93, 0xFB, 0x7D, 0xC7, 0x06, 0x44, 0x83, 0xDA, 0x06, 0x99, 0xE8, 0x40, 0x21, 0x76, 0xC6, 0xB2, 0x0F, 0x24, 0x0D, 0x35, 0x87, 0xBC, 0x1B, 0x07, 0x3C, 0x9A, + 0xA0, 0x09, 0xCB, 0xC1, 0xB0, 0x5F, 0x49, 0xCC, 0xBB, 0x25, 0x13, 0x12, 0x96, 0x92, 0xDF, 0x1C, 0xEC, 0xDA, 0x29, 0x54, 0xCC, 0xEC, 0xC1, 0x7B, 0xBB, 0x1D, 0x11, 0x96, 0x4F, 0xAE, 0xB0, 0xF9, + 0xE0, 0x29, 0x21, 0x29, 0x59, 0xB6, 0x8E, 0x4B, 0xE0, 0x66, 0x64, 0xF9, 0x58, 0x74, 0x32, 0xC0, 0x2D, 0xE6, 0x15, 0x88, 0x51, 0x55, 0x57, 0x56, 0x5A, 0x26, 0xA6, 0xEC, 0xD6, 0xB4, 0xDE, 0x47, + 0xF0, 0xB6, 0x47, 0x63, 0x77, 0x81, 0xEC, 0x19, 0x49, 0x32, 0xD2, 0x82, 0xFF, 0x1F, 0x83, 0x5E, 0xB8, 0x09, 0x66, 0xAB, 0xA2, 0x16, 0xB4, 0xE7, 0xF8, 0x8E, 0xAB, 0x97, 0x05, 0x21, 0x26, 0x4D, + 0xB5, 0xD6, 0xF2, 0x83, 0xA4, 0xF6, 0x79, 0x1E, 0x32, 0x9F, 0xB8, 0xCB, 0x54, 0x25, 0xB9, 0x13, 0x9E, 0x96, 0xAB, 0xB3, 0x94, 0x4E, 0x35, 0xBB, 0x88, 0x64, 0x2A, 0xC0, 0xE7, 0xDC, 0xDA, 0xB9, + 0xB5, 0x59, 0xD0, 0x9E, 0x29, 0x55, 0x72, 0xB2, 0x52, 0x92, 0xC0, 0x3C, 0xD5, 0xAB, 0x5E, 0x7B, 0xBE, 0x77, 0x61, 0xD8, 0x58, 0x3F, 0xAD, 0x91, 0x66, 0x91, 0x3F, 0xDE, 0x1B, 0x65, 0x8F, 0x87, + 0x26, 0xC3, 0xF7, 0xE6, 0xD2, 0x65, 0x63, 0x17, 0xDA, 0xAF, 0xB9, 0x2E, 0x78, 0x7D, 0x24, 0xC5, 0xD8, 0x94, 0x7F, 0xF5, 0x95, 0xA5, 0x85, 0x3D, 0x61, 0x11, 0x73, 0xDF, 0x20, 0xF0, 0xAE, 0x01, + 0x50, 0x75, 0x8C, 0x6B, 0x13, 0x1D, 0xFD, 0xEF, 0x36, 0xA0, 0x1D, 0x7C, 0x87, 0x4D, 0x0B, 0x8C, 0xD0, 0xC2, 0x53, 0x83, 0x56, 0x94, 0x06, 0xCB, 0xE4, 0x2A, 0x72, 0xD7, 0x09, 0x7E, 0x84, 0xD9, + 0x82, 0x58, 0x39, 0xEB, 0xD1, 0x4F, 0x17, 0x5E, 0xD5, 0x1E, 0x6A, 0xC1, 0xA3, 0xF7, 0xF7, 0xBE, 0xFF, 0x60, 0xF5, 0xC0, 0x72, 0x73, 0x42, 0xD7, 0xDD, 0x34, 0x76, 0xDC, 0x9A, 0xE0, 0xE2, 0x7E, + 0xDB, 0xB8, 0x86, 0xBF, 0xA0, 0x0D, 0x36, 0xFE, 0x80, 0xDA, 0x81, 0x6A, 0x45, 0xE0, 0xC8, 0x00, 0x0B, 0x6E, 0x23, 0xE9, 0xB5, 0xCA, 0xD0, 0x13, 0xB6, 0xDE, 0xBF, 0x74, 0x9E, 0xB7, 0x27, 0xB8, + 0xD8, 0x3B, 0xFE, 0x26, 0xF6, 0xC5, 0x99, 0xD5, 0xBD, 0x45, 0xB5, 0x82, 0xB8, 0x4F, 0x4F, 0xC8, 0x34, 0x10, 0xEE, 0x2A, 0x67, 0x5C, 0x66, 0x14, 0x5F, 0x52, 0xCF, 0x36, 0x83, 0x29, 0x0C, 0xC7, + 0x2A, 0x29, 0x28, 0x5D, 0x70, 0x66, 0x7A, 0x3A, 0x31, 0x58, 0x93, 0x54, 0xD9, 0x19, 0x31, 0x62, 0x5F, 0xFA, 0xCF, 0xB7, 0xE0, 0x2C, 0x03, 0xFE, 0x48, 0x09, 0x2A, 0x12, 0x0E, 0x5F, 0x43, 0x12, + 0x76, 0xE8, 0x37, 0x4D, 0xBE, 0x15, 0x40, 0x96, 0xC8, 0x6C, 0x58, 0x79, 0x10, 0xF5, 0x05, 0x1A, 0x86, 0x14, 0x17, 0xC0, 0x6A, 0x73, 0x48, 0x0C, 0xE3, 0x19, 0x5C, 0xC9, 0x99, 0xF6, 0xB8, 0xB3, + 0x01, 0x9B, 0x22, 0x37, 0x96, 0xC5, 0xE1, 0x1F, 0x73, 0x42, 0xC9, 0x74, 0x6A, 0xED, 0xBF, 0xA9, 0x44, 0xCD, 0x79, 0xB8, 0x5C, 0x10, 0x00, 0x07, 0xBB, 0x58, 0x69, 0x84, 0x3A, 0x23, 0xAD, 0x06, + 0xD8, 0x1F, 0x5C, 0xB2, 0x9D, 0xD1, 0x7B, 0xCE, 0xE7, 0x55, 0x72, 0xB9, 0xE0, 0xCF, 0xDB, 0xD5, 0xA8, 0x3A, 0x30, 0x57, 0x44, 0x2D, 0xF0, 0x00, 0xDA, 0x7A, 0x3A, 0xA6, 0xFC, 0x5F, 0xB2, 0x89, + 0xA1, 0x29, 0x99, 0x24, 0xD9, 0x23, 0x1F, 0xE1, 0xD0, 0xCF, 0x3C, 0x17, 0xF1, 0x80, 0x3F, 0x61, 0x43, 0xC0, 0x97, 0xF9, 0x54, 0x2C, 0x9A, 0xBB, 0x8F, 0x98, 0x77, 0xE4, 0xAE, 0xC5, 0x4A, 0xB9, + 0x39, 0x93, 0xDC, 0x49, 0x87, 0xDF, 0x67, 0x80, 0x8B, 0xF7, 0xBE, 0xDE, 0xA8, 0x6B, 0x5C, 0x83, 0xD2, 0x48, 0xE9, 0x5E, 0xA3, 0x02, 0x45, 0x3F, 0x5F, 0x6B, 0x7F, 0xF5, 0xB5, 0xF5, 0x8B, 0x65, + 0xD9, 0x32, 0xD2, 0xBF, 0x73, 0x7C, 0x51, 0x89, 0x3D, 0x89, 0xF0, 0x7D, 0xA5, 0xBF, 0xEA, 0x79, 0xD7, 0xE7, 0xFB, 0x2A, 0xAB, 0x82, 0x33, 0xA2, 0x7E, 0xB4, 0x4C, 0x68, 0x58, 0x05, 0x1D, 0x92, + 0xB9, 0x98, 0xBC, 0x47, 0x51, 0xA4, 0x90, 0x2A, 0xA2, 0x22, 0xDE, 0x2D, 0x5C, 0xDC, 0xEC, 0x26, 0xB3, 0x6D, 0xBA, 0x47, 0xCC, 0xEB, 0x41, 0xFB, 0x19, 0x2D, 0xDF, 0xFD, 0x55, 0x12, 0xD8, 0x2B, + 0x1B, 0xD3, 0x4D, 0x1E, 0xAA, 0x42, 0xF8, 0xCC, 0x50, 0x3F, 0x23, 0x85, 0x92, 0x42, 0x07, 0x9C, 0xBC, 0x1A, 0x55, 0xF0, 0x95, 0xAB, 0xB3, 0xC1, 0x87, 0x9F, 0xD1, 0xB4, 0x85, 0x04, 0xD8, 0x05, + 0x4C, 0x15, 0xEB, 0x3E, 0xBF, 0x54, 0xA3, 0x2C, 0x5B, 0x62, 0xC0, 0x55, 0x55, 0xE4, 0xAC, 0x60, 0x36, 0x91, 0x9B, 0xB9, 0xA1, 0xBB, 0x53, 0x9E, 0x78, 0x86, 0x7A, 0x74, 0xF5, 0x3C, 0x23, 0xB1, + 0xA1, 0x35, 0x98, 0x7D, 0x8B, 0xDD, 0x63, 0xE0, 0x92, 0xAB, 0x2B, 0xF1, 0xD8, 0xF6, 0x60, 0x38, 0xE1, 0x49, 0xAE, 0x41, 0x0B, 0x09, 0xAB, 0x25, 0xB4, 0xFE, 0x65, 0x53, 0xB3, 0x0E, 0x7B, 0xA7, + 0xBF, 0x01, 0x36, 0x36, 0x8E, 0x3B, 0x8B, 0x73, 0x23, 0xA1, 0x24, 0x89, 0x02, 0x94, 0x7B, 0x2A, 0x39, 0x85, 0xB5, 0xC5, 0xCB, 0x80, 0x27, 0xAE, 0xF8, 0xA9, 0xE3, 0x42, 0xA3, 0xB7, 0x54, 0x3C, + 0x31, 0x54, 0x72, 0x49, 0xFC, 0x77, 0x7C, 0x59, 0x2A, 0x31, 0xB8, 0x5B, 0x4B, 0x07, 0xE0, 0xAD, 0x87, 0x61, 0x2C, 0x3D, 0xF4, 0x9B, 0x9E, 0xB6, 0x6A, 0x53, 0xF4, 0x11, 0xC6, 0xD6, 0xDE, 0x9F, + 0x26, 0x86, 0x95, 0x07, 0x74, 0x80, 0x6A, 0xD0, 0xCE, 0xBF, 0x25, 0x4C, 0x18, 0x2F, 0x3A, 0x5D, 0xF9, 0xE4, 0x29, 0xF0, 0x79, 0x2E, 0x96, 0x35, 0x95, 0xB8, 0x42, 0x6B, 0xB0, 0xCB, 0x53, 0x62, + 0x75, 0x36, 0x26, 0x5C, 0x4F, 0x63, 0x46, 0xB4, 0xB0, 0x72, 0xEA, 0xB4, 0xD1, 0xE6, 0x87, 0xA4, 0xDE, 0x7B, 0x82, 0x89, 0x90, 0xEB, 0xF3, 0x38, 0x1F, 0x0B, 0x70, 0xE9, 0x26, 0xD6, 0x7B, 0x76, + 0x89, 0x73, 0xF1, 0x02, 0x40, 0x80, 0xBD, 0x40, 0xC6, 0x7B, 0x81, 0x04, 0x09, 0x34, 0xD1, 0xC3, 0xC3, 0x77, 0x4D, 0xDE, 0x93, 0x28, 0xBE, 0x69, 0xBB, 0xD5, 0xDF, 0xE3, 0xF2, 0x80, 0xDB, 0x77, + 0xFF, 0xC1, 0xA7, 0x8D, 0x11, 0x13, 0x34, 0xB4, 0x21, 0x97, 0x00, 0x2B, 0xD8, 0x5C, 0xD7, 0xCD, 0xF7, 0xCB, 0xB6, 0xED, 0x3F, 0x41, 0xCB, 0xB9, 0xAD, 0x48, 0x1F, 0x44, 0xA3, 0x35, 0x11, 0x55, + 0xA5, 0x22, 0x35, 0x0A, 0x65, 0x8F, 0x69, 0x92, 0x11, 0xD7, 0xAA, 0x5E, 0x68, 0xA5, 0x27, 0x94, 0x76, 0xC0, 0x0B, 0xD9, 0xEE, 0x01, 0x0C, 0xEC, 0x6E, 0x51, 0x02, 0xD2, 0x70, 0x54, 0xC9, 0x74, + 0xD1, 0x6B, 0xE4, 0xA6, 0xC6, 0x85, 0x99, 0xAE, 0x83, 0x01, 0x9C, 0xB1, 0x32, 0x4E, 0x35, 0x10, 0x4F, 0x10, 0x5A, 0x59, 0xE6, 0xCF, 0x07, 0x67, 0x30, 0xF3, 0x3A, 0x03, 0xED, 0xD7, 0xC9, 0x2E, + 0x07, 0x36, 0xB5, 0x42, 0x98, 0x79, 0x0C, 0xA8, 0xD5, 0x28, 0x72, 0x74, 0x28, 0x23, 0x73, 0x19, 0x9E, 0x90, 0xB9, 0x49, 0x13, 0xB9, 0x9C, 0x06, 0xD7, 0xD5, 0xB6, 0xC4, 0x18, 0xF5, 0x5B, 0x66, + 0x14, 0x13, 0x31, 0x13, 0x0E, 0x6B, 0xD5, 0x61, 0x52, 0xB8, 0xDB, 0x19, 0xB2, 0xFB, 0x1B, 0xB6, 0x5C, 0x8D, 0x21, 0xFC, 0xD4, 0xBE, 0x45, 0x1A, 0x4A, 0x1C, 0x0F, 0xEE, 0x73, 0xDB, 0xC3, 0x55, + 0x7D, 0x36, 0x2C, 0x45, 0x3D, 0x8E, 0x6A, 0x43, 0xE9, 0x9E, 0x47, 0x97, 0xD1, 0xF2, 0x5B, 0x1A, 0x58, 0x98, 0x14, 0x81, 0x1D, 0x66, 0xB7, 0x31, 0xA7, 0x5E, 0x99, 0x3F, 0xF1, 0xD3, 0xBC, 0x42, + 0x11, 0xF8, 0xC1, 0x51, 0x0B, 0x90, 0x40, 0x50, 0x68, 0x94, 0xB8, 0x6B, 0xA9, 0xFB, 0xA3, 0x55, 0x49, 0x61, 0xDF, 0x34, 0xFD, 0xB7, 0x65, 0x5F, 0xD9, 0x28, 0x37, 0x8B, 0x4E, 0x65, 0x00, 0x14, + 0x77, 0xD1, 0xFC, 0xF1, 0x8C, 0xB7, 0x1C, 0x5E, 0x41, 0x71, 0x69, 0x6F, 0x33, 0xB2, 0xB6, 0x76, 0x30, 0x38, 0xD5, 0x12, 0xAC, 0xB0, 0xF7, 0xFE, 0xEE, 0x76, 0xF0, 0xFB, 0x16, 0x4E, 0x30, 0xFE, + 0xB7, 0xD6, 0x37, 0xB3, 0xAB, 0x1E, 0x7F, 0x25, 0x1E, 0xF8, 0xC0, 0x54, 0x31, 0x46, 0x1C, 0x3A, 0xB9, 0x0F, 0x05, 0x7D, 0xA0, 0xF4, 0xD8, 0xC3, 0xB3, 0x78, 0x7A, 0xE5, 0x8C, 0xB0, 0x13, 0x6D, + 0x68, 0xAC, 0xB6, 0x40, 0x7B, 0xCF, 0x67, 0x16, 0x20, 0x72, 0x3A, 0x02, 0x30, 0xD4, 0xF7, 0xDD, 0x7A, 0xDE, 0x77, 0x0C, 0x41, 0x8F, 0xCA, 0xD9, 0x97, 0x8F, 0x7C, 0x96, 0x22, 0x26, 0xCA, 0x6D, + 0x65, 0x79, 0xBA, 0xDC, 0x67, 0x52, 0x23, 0x7C, 0x99, 0xD2, 0x4C, 0xA8, 0x04, 0xE9, 0xF1, 0xFC, 0xDC, 0x9A, 0xAA, 0x11, 0x1F, 0x2C, 0x90, 0x5E, 0xF0, 0x31, 0x69, 0x0D, 0x17, 0x65, 0xE8, 0x21, + 0x93, 0x8A, 0x0B, 0x78, 0x46, 0xC3, 0xBB, 0x80, 0xDB, 0xEF, 0x95, 0x30, 0xC6, 0x8C, 0xAA, 0x0A, 0xDA, 0x96, 0x2A, 0x59, 0x5F, 0xD9, 0xE7, 0xAB, 0xD9, 0xE1, 0xF7, 0x6F, 0xF2, 0x97, 0xE1, 0x78, + 0x50, 0x54, 0x13, 0xEE, 0x95, 0xFC, 0x0A, 0x95, 0x8D, 0x72, 0x0C, 0x2A, 0x23, 0x86, 0xA1, 0x64, 0x50, 0xF9, 0x7D, 0xE5, 0x8E, 0xE2, 0x27, 0xBF, 0xA3, 0x3C, 0xAA, 0xC0, 0x3F, 0x13, 0x5A, 0x83, + 0x45, 0x46, 0x9F, 0x26, 0xC7, 0x70, 0x26, 0x91, 0x5E, 0xE2, 0x0F, 0xBD, 0x82, 0xB0, 0x9B, 0x02, 0xFE, 0xA7, 0x7A, 0xBC, 0xFB, 0x9D, 0xA8, 0x94, 0xD8, 0x67, 0x6E, 0x16, 0x0F, 0x1E, 0x1C, 0xEA, + 0x42, 0x0B, 0x2C, 0xFE, 0x14, 0xFF, 0x08, 0xE1, 0x65, 0x0D, 0x56, 0x5B, 0x6C, 0xDF, 0x6A, 0xD7, 0xEE, 0x51, 0x3D, 0xC1, 0xE7, 0x34, 0x30, 0x96, 0xDD, 0x26, 0x5C, 0x45, 0x9F, 0xA1, 0x7C, 0x55, + 0xE5, 0xD6, 0xC6, 0x38, 0x28, 0xBC, 0xC4, 0xB7, 0x2A, 0x2A, 0x02, 0x7C, 0x31, 0xD2, 0x43, 0x8A, 0x7B, 0xFF, 0x42, 0x77, 0x3F, 0xED, 0x94, 0x35, 0xC3, 0xC6, 0xED, 0x66, 0x4D, 0x35, 0x41, 0x86, + 0x58, 0xCB, 0x13, 0x37, 0x43, 0xF4, 0x82, 0x73, 0x2F, 0x6F, 0xB2, 0xC8, 0x9C, 0x68, 0x00, 0x05, 0x20, 0x9D, 0xFB, 0xEE, 0xAB, 0x70, 0x2A, 0x39, 0x11, 0xA8, 0x7D, 0xD5, 0x5E, 0xF3, 0x9F, 0x40, + 0x93, 0x70, 0xBE, 0x94, 0x88, 0x84, 0x42, 0xB0, 0x8D, 0xB3, 0x37, 0x08, 0xBC, 0xB3, 0x1A, 0x14, 0x07, 0x30, 0x3B, 0x4F, 0xED, 0xF3, 0x11, 0xC1, 0x52, 0x63, 0x57, 0x9F, 0x81, 0x74, 0x6C, 0xED, + 0xFB, 0x79, 0x0C, 0xA0, 0x30, 0x4C, 0x88, 0xFC, 0xCA, 0x59, 0x56, 0xE9, 0xF8, 0x19, 0xFE, 0xFF, 0xAC, 0x13, 0xC6, 0x4D, 0x96, 0xC4, 0x3C, 0x98, 0xD8, 0x8F, 0xEC, 0x8F, 0xD9, 0x83, 0xC1, 0xC5, + 0x19, 0xCB, 0x88, 0x4D, 0x2E, 0x7A, 0x90, 0xCD, 0xF3, 0x65, 0xFE, 0x5F, 0xB5, 0xDA, 0x8F, 0xAB, 0x74, 0xF0, 0x73, 0xBA, 0x25, 0x8D, 0x26, 0x4F, 0x94, 0x2D, 0x14, 0xD6, 0xE2, 0xE9, 0x08, 0x29, + 0xAE, 0x35, 0x74, 0x6D, 0x05, 0x7A, 0x18, 0x0E, 0x56, 0x38, 0x42, 0xF5, 0x4C, 0x4B, 0xC7, 0xD5, 0x00, 0x49, 0x43, 0x24, 0x72, 0xD1, 0xED, 0xF1, 0x38, 0xF2, 0xE5, 0x86, 0x26, 0xAB, 0x8C, 0x96, + 0xE6, 0x00, 0xED, 0x19, 0x36, 0xF3, 0x38, 0x80, 0xF4, 0xF2, 0x20, 0x1B, 0x61, 0x07, 0xC4, 0xEF, 0xB9, 0xC0, 0x2E, 0xCF, 0x31, 0x44, 0xE3, 0xAC, 0x55, 0xB0, 0xEE, 0x51, 0x68, 0xA7, 0x93, 0xB1, + 0x5D, 0xB4, 0xA6, 0x1B, 0xFF, 0xFC, 0x8B, 0xE4, 0xA3, 0x80, 0x40, 0xA0, 0x6C, 0x31, 0xF5, 0x15, 0x2D, 0x7C, 0x95, 0xF8, 0xC4, 0x94, 0x45, 0x12, 0x4D, 0x07, 0x20, 0x95, 0xFC, 0x14, 0xF6, 0x79, + 0xDF, 0x55, 0xDC, 0x1E, 0x7F, 0xBE, 0x48, 0x83, 0xDA, 0xA3, 0x50, 0xF2, 0x16, 0x98, 0xEB, 0x78, 0xB2, 0x9A, 0xDB, 0xD0, 0x71, 0x53, 0x58, 0xF9, 0x65, 0x27, 0x8A, 0xF8, 0x67, 0xC1, 0x2E, 0x2B, + 0xB1, 0x9F, 0xFA, 0x16, 0x50, 0x27, 0x69, 0xF4, 0xFB, 0xDB, 0x20, 0x82, 0x2D, 0x1D, 0xE1, 0xFB, 0x6E, 0x41, 0x6D, 0x82, 0x29, 0x32, 0xB5, 0xCD, 0x5B, 0x37, 0x0A, 0x58, 0x65, 0x56, 0x07, 0x56, + 0xD7, 0x6D, 0x8C, 0x2F, 0xE4, 0x70, 0x4E, 0x0B, 0x15, 0x83, 0xEB, 0x5D, 0x23, 0x5E, 0xC3, 0xFE, 0x7F, 0xF4, 0x98, 0xE1, 0x35, 0x61, 0x00, 0xC5, 0x80, 0x76, 0x3E, 0xB5, 0xF2, 0x36, 0x35, 0x62, + 0x0C, 0xF6, 0xCC, 0x56, 0xE7, 0x4B, 0x48, 0x22, 0x3C, 0x70, 0xB5, 0xE5, 0x23, 0xAC, 0x61, 0xEA, 0xAE, 0xF8, 0x8E, 0x4D, 0xD1, 0x50, 0x5D, 0x25, 0xC9, 0x65, 0x8B, 0x96, 0xE9, 0x32, 0xCE, 0x0B, + 0xD0, 0xEF, 0xFE, 0x80, 0xBA, 0xA5, 0xD1, 0x05, 0xA6, 0x51, 0x4B, 0x25, 0x57, 0x8D, 0x1F, 0x3F, 0xCC, 0x8F, 0xF5, 0xF9, 0x3A, 0x7C, 0xDD, 0xCC, 0xE0, 0x84, 0x0F, 0x63, 0x1B, 0xE0, 0x2B, 0xCA, + 0x85, 0x20, 0x98, 0xDC, 0xFA, 0x06, 0x56, 0xF0, 0x8A, 0xF1, 0xBD, 0xC8, 0xE2, 0x4A, 0x27, 0x46, 0x74, 0x16, 0xF4, 0x87, 0xAD, 0x02, 0x60, 0x22, 0xDD, 0x5E, 0x1E, 0x1E, 0xFD, 0xC9, 0xC2, 0xB4, + 0x71, 0xE3, 0x26, 0x53, 0x65, 0xF2, 0x0B, 0xC8, 0x21, 0x86, 0x37, 0x66, 0x25, 0x5D, 0x0A, 0xAC, 0x67, 0xB6, 0x58, 0xE6, 0x63, 0x3F, 0xD2, 0xC9, 0x3F, 0x80, 0xE5, 0x55, 0x5C, 0x6B, 0x3F, 0x9B, + 0x9C, 0x54, 0x02, 0x62, 0xF9, 0x2E, 0x57, 0x5E, 0xCA, 0x8C, 0xBD, 0xDE, 0xA2, 0x5E, 0x35, 0x59, 0x9F, 0xAF, 0xE0, 0x90, 0x20, 0x1D, 0x53, 0x1A, 0x96, 0xA6, 0x59, 0x5F, 0x6B, 0xC0, 0xA0, 0x83, + 0x47, 0xF4, 0x54, 0xFC, 0x12, 0x6A, 0x16, 0x21, 0x64, 0xA0, 0xD5, 0x07, 0x39, 0xF3, 0x0A, 0xB2, 0x29, 0x89, 0xF8, 0x88, 0xE4, 0xDF, 0xA3, 0x56, 0x13, 0x7A, 0x3E, 0x65, 0xEC, 0xB5, 0xF4, 0x7E, + 0x20, 0x0E, 0x73, 0x36, 0xA2, 0xF0, 0xA5, 0xC5, 0x47, 0xA2, 0x36, 0x7F, 0x1D, 0x0F, 0xDE, 0xA8, 0x9D, 0x00, 0x69, 0x8D, 0x96, 0x2E, 0x62, 0xE8, 0xDA, 0xA5, 0x70, 0xEE, 0x07, 0x7B, 0x9E, 0xB8, + 0x18, 0xED, 0x82, 0x75, 0xB2, 0x3E, 0x73, 0x39, 0xFA, 0x3A, 0x6C, 0x9E, 0xF0, 0xD3, 0xC9, 0x78, 0xEE, 0xF7, 0x5B, 0xC9, 0x77, 0xAA, 0xFE, 0x87, 0xB1, 0xA4, 0x1F, 0xED, 0x4C, 0x7D, 0xA1, 0x7E, + 0x2B, 0xBE, 0xCC, 0xA8, 0xF4, 0x06, 0xF0, 0x40, 0xB1, 0x6F, 0xDD, 0xFB, 0x2E, 0x8F, 0x47, 0x0C, 0x25, 0x40, 0x9B, 0x8C, 0x7C, 0x13, 0x88, 0xE6, 0x08, 0xEB, 0xBA, 0xE2, 0x67, 0xF7, 0x7C, 0x5F, + 0xE0, 0x10, 0xF6, 0x91, 0x7B, 0xC6, 0xCA, 0x7B, 0xF6, 0x86, 0x5F, 0xAA, 0x73, 0xE1, 0x0F, 0x2F, 0x60, 0xD2, 0x2D, 0xB2, 0x4A, 0x21, 0x71, 0x81, 0xBE, 0x56, 0xFD, 0x47, 0x3E, 0xE7, 0xAF, 0x5E, + 0xD5, 0x60, 0x9A, 0xDA, 0x02, 0x36, 0xFA, 0xB3, 0x06, 0x6C, 0x3D, 0xAD, 0x28, 0xA2, 0x4F, 0x67, 0xD4, 0xCC, 0x1C, 0xEF, 0xE6, 0x10, 0x6F, 0x5E, 0x54, 0x27, 0xAC, 0xCD, 0xC7, 0x3F, 0xF8, 0x85, + 0x76, 0xA2, 0x7A, 0xEB, 0xE7, 0x1A, 0x33, 0xDB, 0x3C, 0x08, 0x02, 0xD6, 0x97, 0x18, 0x95, 0x6C, 0xD9, 0xD1, 0x5A, 0xAA, 0x9A, 0x2D, 0xE3, 0xAC, 0x62, 0x10, 0x10, 0x0A, 0x2E, 0x39, 0xAF, 0x5B, + 0xA9, 0x1D, 0xFA, 0x21, 0x8C, 0x53, 0x72, 0x66, 0x06, 0x2E, 0x32, 0x6E, 0x2F, 0xF8, 0xC4, 0x4D, 0x17, 0x80, 0xFB, 0xAF, 0xF4, 0xAD, 0xBA, 0x82, 0x71, 0x17, 0xE0, 0xBC, 0xB7, 0xA4, 0xC8, 0xF2, + 0x61, 0x39, 0x81, 0x71, 0x3F, 0xA5, 0x98, 0xA4, 0x68, 0x3A, 0x46, 0x70, 0x85, 0x4C, 0x94, 0x67, 0xF2, 0x5A, 0x65, 0x6D, 0xDB, 0x6E, 0x7C, 0x3E, 0xF1, 0x92, 0xEB, 0xBD, 0xEE, 0x15, 0x3A, 0x59, + 0x41, 0x61, 0x95, 0x26, 0xB3, 0x17, 0x87, 0x54, 0x4F, 0xE2, 0x31, 0x2A, 0x28, 0x98, 0x9C, 0x6A, 0xA3, 0xAC, 0xC0, 0xFE, 0x44, 0x23, 0x14, 0xFD, 0xFB, 0xD8, 0x08, 0x7F, 0x2B, 0x75, 0x5E, 0xB4, + 0xB7, 0x35, 0x55, 0x76, 0x28, 0x3F, 0xA8, 0x6C, 0xD2, 0xD9, 0xEC, 0x1A, 0x6B, 0xD9, 0x4E, 0x6C, 0x5D, 0x72, 0x82, 0x02, 0xEC, 0x0B, 0x6E, 0xDF, 0xE1, 0xF3, 0x35, 0x84, 0x11, 0xC4, 0x9E, 0xC1, + 0x10, 0x63, 0xAC, 0x1E, 0xDE, 0xB2, 0x1B, 0x95, 0xD7, 0x13, 0xD9, 0x0B, 0xE4, 0x96, 0xD8, 0x55, 0x84, 0xAA, 0x64, 0x25, 0x47, 0x14, 0x80, 0x84, 0x4E, 0x5B, 0xE2, 0xD7, 0x05, 0x3E, 0x87, 0x22, + 0x03, 0x64, 0x79, 0xBD, 0xCB, 0x36, 0x38, 0x35, 0xBB, 0x08, 0xB0, 0x10, 0xDD, 0x0C, 0x08, 0x0E, 0x3D, 0x85, 0x24, 0xAE, 0x62, 0x21, 0x3E, 0x20, 0x8E, 0xC4, 0x12, 0xD0, 0x1F, 0xC9, 0xCE, 0xFA, + 0x9C, 0x0A, 0xBD, 0x39, 0x64, 0x96, 0x45, 0x51, 0x84, 0xDB, 0x24, 0x4A, 0xD6, 0xBE, 0xB4, 0x5F, 0xB7, 0x68, 0x47, 0x91, 0x62, 0x47, 0x44, 0x33, 0x52, 0x0C, 0xE0, 0x63, 0x03, 0xFF, 0xC6, 0x06, + 0x07, 0xDD, 0x43, 0x29, 0x62, 0x88, 0x4F, 0x8A, 0xA6, 0x54, 0x39, 0x98, 0xE1, 0xFB, 0x24, 0xDA, 0xF8, 0xAB, 0x3F, 0xF8, 0x62, 0xA8, 0x16, 0xA3, 0x98, 0x28, 0xF5, 0x7B, 0x54, 0x7A, 0xE7, 0x66, + 0x98, 0x3F, 0x7C, 0xFA, 0xC8, 0x50, 0x23, 0xDC, 0x65, 0x53, 0x43, 0x12, 0x74, 0xB8, 0x40, 0x19, 0xDB, 0xD8, 0x5D, 0x2C, 0x42, 0x9D, 0x2B, 0x01, 0xE3, 0xC0, 0xA5, 0xDE, 0x1E, 0x6C, 0xC8, 0x5E, + 0x62, 0x57, 0x9B, 0x00, 0x12, 0x6E, 0x6F, 0xE8, 0x1A, 0xB2, 0xEC, 0x08, 0x85, 0xD4, 0x30, 0x98, 0xA6, 0xF2, 0x15, 0x94, 0xD6, 0x67, 0x0F, 0x3E, 0xAB, 0x54, 0xEF, 0x3E, 0x30, 0xC7, 0x38, 0x96, + 0x46, 0x1F, 0xE3, 0xCA, 0x4E, 0x8E, 0xD9, 0x29, 0x3E, 0x4F, 0x27, 0x6E, 0x18, 0xAA, 0xC8, 0x54, 0x46, 0xC0, 0xC2, 0x34, 0xFF, 0x6F, 0x9A, 0xE1, 0x1A, 0x09, 0x89, 0x9B, 0x3D, 0x22, 0x1C, 0xC6, + 0xC4, 0xB3, 0x63, 0xF7, 0xBE, 0x27, 0xAD, 0xF3, 0xF5, 0x1C, 0xE4, 0xBD, 0x8F, 0x51, 0xC2, 0x1C, 0x7F, 0x44, 0xE3, 0x08, 0x3C, 0x8D, 0x04, 0x71, 0x24, 0x08, 0x4C, 0x1E, 0xDB, 0x09, 0x0A, 0x7D, + 0x80, 0x56, 0x51, 0x7B, 0xBB, 0xD1, 0xF1, 0x87, 0xC4, 0x27, 0xDD, 0xA5, 0x9E, 0x54, 0x5E, 0x8C, 0x60, 0x03, 0xCA, 0x0B, 0xC5, 0xBD, 0x38, 0x9E, 0xBD, 0x90, 0xB9, 0x97, 0x08, 0xC3, 0xD3, 0xC7, + 0x40, 0x44, 0xEB, 0x2A, 0xB3, 0xCA, 0x6F, 0x72, 0xD4, 0xB2, 0xD4, 0x91, 0x02, 0xB9, 0x74, 0x89, 0x64, 0x56, 0xFC, 0x67, 0x38, 0xE9, 0x0B, 0x94, 0x8C, 0x62, 0xE0, 0x16, 0x17, 0x14, 0x87, 0x1F, + 0x57, 0x41, 0x9E, 0xCB, 0xAA, 0x16, 0xD0, 0x16, 0x65, 0xAC, 0xEB, 0x39, 0x69, 0xB4, 0x84, 0xA2, 0xE0, 0x29, 0xED, 0x6A, 0x73, 0x30, 0x0E, 0x06, 0xC8, 0x50, 0xAF, 0xEF, 0xFC, 0x08, 0xCE, 0x29, + 0x61, 0x85, 0x4E, 0x9A, 0xA0, 0x65, 0x38, 0xFF, 0x6D, 0x9F, 0x5A, 0xEE, 0xAF, 0x57, 0x76, 0x1C, 0xB6, 0xAE, 0x36, 0x87, 0x1D, 0xC4, 0x17, 0x33, 0x2F, 0x30, 0x63, 0xBF, 0x91, 0x37, 0x21, 0x22, + 0x68, 0xC3, 0x1F, 0x27, 0x8D, 0xC6, 0x85, 0xC1, 0xAD, 0x44, 0xD2, 0x22, 0x56, 0x6F, 0x9F, 0x18, 0x82, 0x3D, 0x55, 0x0E, 0x89, 0x86, 0x51, 0xD7, 0x65, 0x57, 0x1A, 0x10, 0x69, 0xB8, 0x27, 0x48, + 0x61, 0x85, 0x34, 0x59, 0xCF, 0x49, 0xDB, 0x92, 0x37, 0x44, 0xC9, 0xC5, 0xC9, 0x3D, 0xD2, 0x6F, 0x66, 0x3F, 0x9A, 0xDD, 0xD0, 0xBF, 0x56, 0x38, 0x05, 0xB4, 0xB7, 0x47, 0xC0, 0xA6, 0xE5, 0xB5, + 0x86, 0x90, 0x0C, 0x57, 0x25, 0x96, 0xF2, 0x12, 0x01, 0xD3, 0x74, 0x55, 0x53, 0xCA, 0x09, 0xD2, 0x19, 0xCB, 0x01, 0x79, 0xF0, 0xB1, 0x00, 0x17, 0xF0, 0xF1, 0x4D, 0x5A, 0xF3, 0xB9, 0x4B, 0xB4, + 0xA9, 0x38, 0x61, 0x78, 0xA8, 0x2D, 0x2B, 0x14, 0x11, 0xED, 0x8B, 0x95, 0xAC, 0x40, 0xAE, 0x73, 0xB2, 0x36, 0xD9, 0xB7, 0x83, 0x25, 0x0F, 0x1B, 0x9B, 0xBD, 0xBD, 0x88, 0xC0, 0x9E, 0xEB, 0x29, + 0x0A, 0x83, 0xD8, 0x0A, 0x44, 0x47, 0x60, 0xB9, 0x83, 0xB2, 0x70, 0x20, 0xF1, 0x28, 0xED, 0x00, 0xE5, 0xD1, 0xD3, 0xBB, 0xC8, 0xCE, 0x86, 0x21, 0x4E, 0xB5, 0xF5, 0x33, 0xCC, 0x80, 0xF2, 0x78, + 0xB1, 0x92, 0xB5, 0x7A, 0xBB, 0x0F, 0xFA, 0x70, 0x3E, 0xBF, 0x0B, 0xAA, 0xE4, 0x92, 0x6D, 0x63, 0xC0, 0xFF, 0x51, 0x8A, 0x9B, 0xBE, 0xB3, 0x48, 0xD5, 0xB5, 0xA0, 0x4F, 0x6F, 0xFF, 0xCF, 0xD3, + 0xA4, 0x25, 0xE5, 0x08, 0xBD, 0xAB, 0x88, 0xB4, 0x05, 0x7D, 0x94, 0xD6, 0xF8, 0xB1, 0xB0, 0x56, 0x78, 0x3F, 0xE4, 0x0B, 0xE6, 0xD6, 0xEF, 0xDF, 0x53, 0x1F, 0x52, 0x81, 0x15, 0xE2, 0xB3, 0x21, + 0x11, 0xD2, 0xB7, 0xCE, 0x59, 0x90, 0x84, 0xE2, 0x0F, 0x9E, 0xAD, 0x59, 0x5A, 0xC9, 0x15, 0xCB, 0xAB, 0x2A, 0x48, 0x6C, 0x98, 0x5F, 0xB5, 0x0F, 0x6E, 0x2F, 0x3E, 0x16, 0x02, 0xD8, 0xE8, 0xCF, + 0xA7, 0x68, 0x5A, 0xAA, 0x30, 0x5C, 0x06, 0x0F, 0x11, 0xDB, 0x98, 0x07, 0x40, 0xBB, 0xF4, 0xBD, 0xF4, 0xA7, 0x1A, 0x1C, 0x7E, 0x37, 0xC6, 0xC6, 0xE8, 0x91, 0x20, 0xAD, 0x91, 0x2C, 0x2F, 0x2A, + 0xC0, 0x25, 0x0F, 0x0F, 0xCE, 0x82, 0x6C, 0x55, 0xB6, 0xFB, 0x0F, 0x63, 0x8D, 0xC0, 0xC5, 0x5E, 0x32, 0x7E, 0x92, 0x2D, 0xC4, 0x53, 0x75, 0x18, 0x69, 0xCD, 0xAB, 0xBC, 0x95, 0xA3, 0xC3, 0x50, + 0x36, 0x8A, 0xF7, 0xAB, 0x4C, 0x17, 0xB0, 0x1D, 0x8B, 0xC4, 0x77, 0x74, 0xB9, 0x01, 0xA1, 0x8A, 0xDB, 0x86, 0x98, 0x10, 0x37, 0x67, 0x21, 0xDC, 0x23, 0x3D, 0x81, 0x1D, 0xF2, 0x20, 0x8C, 0x04, + 0xDF, 0x9B, 0xEE, 0xB8, 0x28, 0xB0, 0x02, 0xEA, 0xA1, 0xF8, 0x64, 0x09, 0x1C, 0x1C, 0xD0, 0x90, 0xEA, 0x6F, 0xAB, 0xCC, 0x0B, 0x06, 0x4E, 0xD2, 0x91, 0x6A, 0xA1, 0x0F, 0x14, 0x4E, 0xE4, 0x47, + 0x0A, 0x75, 0xAB, 0x04, 0xF2, 0xCC, 0xA1, 0xD8, 0xAC, 0x42, 0x48, 0x4D, 0xCE, 0x93, 0x46, 0x76, 0xE7, 0x4A, 0x2A, 0x9E, 0x19, 0xB0, 0x96, 0xF1, 0x08, 0x8E, 0xBD, 0x2F, 0xDE, 0x8D, 0x16, 0x78, + 0x46, 0xAA, 0x33, 0xD1, 0x81, 0x31, 0x72, 0xE9, 0x2B, 0x13, 0xB6, 0x70, 0x81, 0xC4, 0x4C, 0x35, 0xF2, 0x55, 0xBB, 0x23, 0x6D, 0x0C, 0xF2, 0x9A, 0x58, 0xD0, 0xCC, 0xDE, 0xC3, 0x70, 0xC8, 0x6F, + 0x84, 0x0D, 0xC6, 0xF9, 0x7A, 0x74, 0xBF, 0xAA, 0xCE, 0xFA, 0xBA, 0x55, 0x65, 0xD7, 0x73, 0x62, 0x3A, 0x24, 0x32, 0x92, 0xE6, 0xDC, 0x76, 0x57, 0x39, 0x23, 0xD5, 0x9A, 0xC4, 0x43, 0xDB, 0x86, + 0xA3, 0x12, 0x9A, 0x54, 0x73, 0xB1, 0x19, 0x4D, 0x21, 0xA4, 0x61, 0xF6, 0x11, 0x4F, 0xDE, 0xC3, 0xA6, 0xD3, 0x8F, 0x28, 0xB3, 0x9B, 0x87, 0xF2, 0xEA, 0x06, 0x86, 0x67, 0x40, 0x94, 0x6B, 0x0D, + 0x09, 0x7A, 0xF4, 0xB2, 0xC0, 0x6D, 0x36, 0xE9, 0xFC, 0xD2, 0x40, 0x48, 0x90, 0x8E, 0x38, 0xA6, 0xF7, 0x6E, 0xAB, 0xBC, 0x19, 0x76, 0x17, 0x92, 0x82, 0xEB, 0x0E, 0x51, 0xD0, 0xE8, 0x3B, 0xE5, + 0xCD, 0x93, 0xE6, 0x14, 0xC1, 0x6B, 0xEC, 0x1E, 0xEC, 0xB9, 0xF1, 0x81, 0x08, 0x61, 0x70, 0x47, 0x59, 0xD1, 0xA0, 0x78, 0x92, 0xBF, 0x52, 0xF5, 0x5F, 0x89, 0x39, 0xA4, 0xDC, 0x30, 0x88, 0xFA, + 0x16, 0x65, 0xF1, 0x35, 0xBD, 0x04, 0x77, 0xD0, 0x2D, 0xCD, 0xE5, 0x7E, 0x0C, 0x1C, 0x0F, 0xAC, 0x0F, 0xA7, 0x0A, 0x25, 0x6F, 0x9B, 0x9B, 0xEB, 0xC7, 0xEB, 0x33, 0xF6, 0x6D, 0xB4, 0xE7, 0x9D, + 0xF4, 0xB0, 0x70, 0xD8, 0x31, 0x81, 0x56, 0xFD, 0x65, 0xE1, 0xB3, 0x6D, 0x37, 0xAC, 0xF9, 0xB0, 0xAA, 0xF0, 0x7C, 0x60, 0x34, 0x37, 0xC4, 0xA3, 0xD2, 0xFA, 0x2D, 0xCE, 0x6B, 0xCF, 0xAF, 0x18, + 0x3F, 0x92, 0x1C, 0x6E, 0xE3, 0xE8, 0x7B, 0xD1, 0x75, 0x05, 0x7B, 0xC9, 0x97, 0xF9, 0x0D, 0x18, 0x59, 0xEF, 0x76, 0x01, 0xE6, 0x8D, 0x35, 0x84, 0x62, 0xAF, 0xE3, 0xBA, 0xD1, 0x92, 0x83, 0x60, + 0xE1, 0xAA, 0xFC, 0xCC, 0x17, 0x0D, 0x0F, 0xD7, 0x65, 0x18, 0x0B, 0x57, 0xB0, 0x33, 0xCF, 0xCC, 0xE2, 0x89, 0x87, 0x8F, 0x41, 0x9B, 0x7D, 0x44, 0x71, 0xB7, 0xB0, 0xF3, 0xBF, 0x42, 0x56, 0xC0, + 0x68, 0xDB, 0xCD, 0xBA, 0x7B, 0x0F, 0x20, 0x2C, 0xC7, 0x52, 0x9A, 0x76, 0xC0, 0x9D, 0xB1, 0x66, 0xA1, 0x98, 0x5E, 0x10, 0xB4, 0x6F, 0x83, 0x0F, 0x08, 0xF7, 0x3E, 0xB2, 0x54, 0xCC, 0x3E, 0x33, + 0xD6, 0x90, 0xDF, 0xAB, 0xED, 0x3F, 0x77, 0xE4, 0xC4, 0x65, 0x47, 0x39, 0x90, 0x9E, 0x86, 0x1D, 0x04, 0x87, 0x49, 0x35, 0xD1, 0x20, 0x5D, 0xF3, 0x94, 0x1B, 0x10, 0x3D, 0x60, 0xF7, 0x1C, 0x36, + 0x2B, 0xF0, 0x21, 0x91, 0x93, 0xF9, 0xAD, 0xAE, 0x49, 0xD3, 0x06, 0xF5, 0x0A, 0x34, 0x79, 0x09, 0x70, 0x8A, 0x41, 0x7C, 0x74, 0xF8, 0xB8, 0xC4, 0x4D, 0x8C, 0x7F, 0xBE, 0xD5, 0x2F, 0x1A, 0x00, + 0x98, 0x88, 0xED, 0x7D, 0xA2, 0x55, 0x12, 0xD7, 0x3C, 0xA3, 0x76, 0x02, 0xD4, 0x6E, 0xEC, 0x02, 0x9D, 0x4F, 0x16, 0x84, 0x91, 0xC7, 0x0F, 0x2D, 0x0F, 0x13, 0x58, 0xCE, 0x37, 0x0C, 0x2C, 0xF2, + 0x82, 0x35, 0x00, 0xE9, 0x89, 0xFB, 0x24, 0x72, 0x3C, 0x21, 0xDD, 0xA0, 0x82, 0x09, 0x05, 0x03, 0x82, 0x09, 0x01, 0x00, 0x94, 0x06, 0xE4, 0xDC, 0xE8, 0x12, 0xBE, 0x92, 0xE1, 0x53, 0xE0, 0x75, + 0x2C, 0xFE, 0x26, 0xC1, 0x12, 0x7E, 0x9C, 0x80, 0xC8, 0x11, 0x3E, 0x12, 0x16, 0x95, 0xF9, 0x01, 0x4E, 0x03, 0xFF, 0xF1, 0xFD, 0x7B, 0xE3, 0xB0, 0xF4, 0x0E, 0xEE, 0x5B, 0x02, 0xF5, 0x60, 0x1E, + 0x2F, 0xC3, 0xAF, 0xF0, 0xCD, 0xF7, 0xE7, 0xE7, 0x34, 0x99, 0x9C, 0x7F, 0xC4, 0xEB, 0x9D, 0xDA, 0x81, 0x8C, 0x52, 0x06, 0x93, 0xFE, 0x38, 0xE4, 0x49, 0xBE, 0x4C, 0xCF, 0x03, 0xFE, 0xA1, 0x72, + 0x8E, 0x4C, 0xCA, 0x64, 0xFD, 0x11, 0x0B, 0xFC, 0x8E, 0xC9, 0xCB, 0x79, 0x50, 0x3B, 0xD5, 0x53, 0xF5, 0x89, 0x9A, 0x2F, 0x63, 0x16, 0x5D, 0x19, 0x32, 0x72, 0x7D, 0xB7, 0x44, 0x72, 0x65, 0xF7, + 0x96, 0xF4, 0xFD, 0xBC, 0xFE, 0xA6, 0xF4, 0x05, 0x9E, 0x88, 0x34, 0x34, 0xC7, 0x98, 0xB8, 0x68, 0xF9, 0x86, 0x60, 0x5D, 0x4D, 0x03, 0xD3, 0x04, 0xB6, 0x77, 0xE3, 0x0F, 0xF7, 0xD7, 0x83, 0x0A, + 0xDD, 0x06, 0x65, 0x2B, 0xCC, 0x1B, 0xF0, 0x4D, 0x33, 0xDF, 0xFE, 0xFC, 0xEF, 0x63, 0x4A, 0xF5, 0xBA, 0xE0, 0xD5, 0xC6, 0xBA, 0xB6, 0xC5, 0x64, 0xF1, 0x95, 0x20, 0x82, 0xAA, 0x38, 0x25, 0x53, + 0x20, 0x01, 0x9C, 0xBC, 0x8E, 0xCA, 0x07, 0x3D, 0x80, 0xAF, 0x0A, 0x59, 0x6E, 0x4D, 0x33, 0xAD, 0x73, 0xB4, 0xF1, 0xED, 0xD4, 0x20, 0xE0, 0x90, 0x0B, 0xED, 0x47, 0x49, 0x5A, 0x88, 0x62, 0xD4, + 0xA9, 0xCD, 0xDE, 0xD0, 0xDE, 0xA7, 0x74, 0xCD, 0xE0, 0x23, 0x8C, 0x71, 0x2B, 0x8A, 0xA9, 0x82, 0x47, 0x56, 0x66, 0x0D, 0x2B, 0x34, 0xE4, 0x7E, 0x4B, 0x59, 0x42, 0x5F, 0x17, 0xA9, 0x60, 0x8D, + 0xAD, 0x38, 0x28, 0xEC, 0x9D, 0x8A, 0xDB, 0x5D, 0xD3, 0x8C, 0x7D, 0x53, 0xDD, 0xA6, 0xDA, 0xC7, 0x4D, 0x3F, 0xD0, 0x3C, 0x00, 0xB5, 0x9E, 0xE9, 0xA0, 0xE5, 0x27, 0x6E, 0x3E, 0x75, 0xD0, 0x13, + 0x61, 0x01, 0x66, 0x49, 0x1D, 0x87, 0x3A, 0x7D, 0xA2, 0xC9, 0xFD, 0xA3, 0x60, 0xA6, 0x47, 0x73, 0x25, 0x00, 0x58, 0x41, 0x8F, 0xA7, 0x62, 0x63, 0x2D, 0xCB, 0x12, 0x63, 0x85, 0x27, 0x32, 0x60, + 0x02, 0x18, 0x67, 0x53, 0xE6, 0xB5, 0xD3, 0x31, 0xE5, 0x64, 0x23, 0xC9, 0x70, 0x9D, 0x34, 0x9C, 0x69, 0x5A, 0x32, 0x8A, 0x56, 0x2B, 0x13, 0x9A, 0xF5, 0x98, 0xF8, 0x5D, 0xCB, 0x35, 0x98, 0x40, + 0x7D, 0x82, 0xF8, 0x49, 0xC2, 0x9A, 0x87, 0xDC, 0x41, 0xFA, 0xA7, 0x69, 0x8F, 0xAC, 0x7F, 0x20, 0x4D, 0x70, 0xD0, 0x7D, 0x4A, 0xDC, 0x1D, 0x68, 0xFB, 0x46, 0x08, 0x63, 0xBB, 0x00, 0x2F, 0x3A, + 0x23, 0x57, 0xCB, 0x65, 0xFB, 0x4B, 0x03, 0xBA, 0xB6, 0x8D, 0xB9, 0xB1, 0x1A, 0x09, 0xC9, 0x02, 0xE8, 0x12, 0x95, 0x91, 0x54, 0x16, 0xB4, 0x51, 0xD8, 0xE5, 0xFB, 0xF7, 0x81, 0x33, 0xBE, 0xD2, + 0x81, 0x81, 0x37, 0x17, 0xE3, 0x74, 0xC5, 0xB4, 0x15, 0xE7, 0x77, 0x3F, 0x95, 0xD8, 0x3D, 0x8B, 0xF9, 0x7D, 0x4A, 0xC4, 0x5E, 0xAC, 0x28, 0x1E, 0x50, 0x89, 0x69, 0x32, 0xF7, 0xEE, 0xA4, 0x83, + 0xE6, 0x98, 0xED, 0xD6, 0x07, 0xC3, 0xFF, 0xDD, 0xD3, 0x4C, 0x56, 0x67, 0x03, 0x28, 0xEB, 0xA5, 0xE1, 0xEB, 0x24, 0x9B, 0x8E, 0x26, 0x85, 0x38, 0xBF, 0x4C, 0xF3, 0x43, 0x2E, 0xD5, 0xA9, 0x33, + 0xB8, 0x2E, 0x6C, 0x0E, 0x96, 0x0D, 0xE1, 0x8A, 0x20, 0x9F, 0xA3, 0x90, 0x96, 0x93, 0x87, 0x88, 0x4D, 0xAD, 0x8D, 0x8E, 0xE7, 0xE6, 0x0A, 0x89, 0x69, 0x90, 0x62, 0x16, 0x2F, 0x90, 0xBB, 0x28, + 0xE4, 0xCC, 0xBA, 0x1A, 0x5F, 0x52, 0x6D, 0xE9, 0xCF, 0x7F, 0xEF, 0xEC, 0x7A, 0x77, 0xDD, 0xA0, 0x7C, 0xD7, 0x00, 0x09, 0xE4, 0x8E, 0xBF, 0x8E, 0xDD, 0x9B, 0x34, 0x87, 0x26, 0xA9, 0x37, 0xE1, + 0x4F, 0xF5, 0xEB, 0x6E, 0x79, 0xE3, 0xDB, 0x1B, 0x60, 0xD7, 0x0A, 0x73, 0x05, 0x11, 0x15, 0x4A, 0x8A, 0xB8, 0x75, 0xF8, 0x6D, 0xEB, 0xCB, 0x9D, 0x79, 0x0F, 0xC4, 0x32, 0x84, 0x4E, 0x90, 0x3C, + 0x8B, 0xD9, 0xFD, 0xB2, 0x8F, 0x99, 0x88, 0xDF, 0xAE, 0xA5, 0x56, 0xE9, 0x20, 0xE5, 0x79, 0x25, 0x47, 0xAE, 0xA7, 0xA4, 0x5B, 0x4C, 0x7E, 0x68, 0x41, 0x61, 0x1E, 0x33, 0x06, 0x4E, 0x5C, 0xB5, + 0x9B, 0xBA, 0xEC, 0xA6, 0x9E, 0x38, 0xA0, 0x99, 0x94, 0xAE, 0xEA, 0x3D, 0x10, 0xF6, 0xFC, 0x53, 0xF6, 0x43, 0x56, 0x2F, 0xA0, 0x0A, 0x34, 0x12, 0xD4, 0xAF, 0xF8, 0x01, 0xD4, 0x8D, 0x0C, 0x58, + 0xBA, 0x05, 0x5A, 0x42, 0xCD, 0xF6, 0xB8, 0xF1, 0x86, 0x16, 0x99, 0xEF, 0xD9, 0xAD, 0x9D, 0xF4, 0xCB, 0xB9, 0x88, 0xE7, 0x22, 0x17, 0x12, 0xBB, 0x42, 0xA4, 0x3B, 0xE8, 0x32, 0x25, 0x09, 0x11, + 0x1D, 0x3A, 0x8E, 0xBC, 0x97, 0xFA, 0xEB, 0xF9, 0xF8, 0x5D, 0x69, 0x20, 0x76, 0x5A, 0x18, 0x2A, 0xD9, 0xC4, 0x54, 0x27, 0x99, 0x31, 0x70, 0x5E, 0xA2, 0x90, 0x3F, 0x6E, 0x18, 0x7D, 0x2A, 0xF6, + 0xA5, 0xE4, 0xA8, 0x30, 0x54, 0x16, 0x8A, 0xA6, 0xA6, 0xF1, 0x27, 0xC8, 0xCE, 0x0C, 0x56, 0xA2, 0xEF, 0x67, 0xDC, 0x1C, 0xD9, 0xB2, 0x2A, 0x51, 0x39, 0xDA, 0xC1, 0x92, 0xFF, 0xC5, 0x3A, 0x13, + 0xEC, 0x52, 0xA3, 0x22, 0x07, 0xA9, 0x6A, 0x4F, 0xED, 0xB1, 0x20, 0x55, 0xFF, 0xDD, 0xBE, 0xE6, 0xAE, 0xF0, 0x72, 0xF7, 0x5D, 0xB7, 0xC6, 0xCD, 0x37, 0xB2, 0x58, 0x9D, 0xC0, 0x0F, 0xBE, 0xF1, + 0x33, 0x3E, 0xB1, 0x13, 0xC8, 0x22, 0x1B, 0xF8, 0x74, 0x0F, 0xD7, 0xBF, 0x7F, 0x39, 0xA5, 0x7E, 0x4A, 0xE2, 0xCE, 0x86, 0xE0, 0xE8, 0xB4, 0xE9, 0x21, 0x4D, 0x67, 0x21, 0x46, 0xED, 0xE9, 0x85, + 0x87, 0x15, 0x71, 0x56, 0x5E, 0x9F, 0x59, 0xCD, 0xA5, 0x92, 0x22, 0xAC, 0x9C, 0x6C, 0x00, 0xD5, 0xA7, 0xC9, 0xD8, 0xA3, 0xE5, 0x46, 0xDE, 0xC8, 0x3C, 0x65, 0x54, 0xEA, 0x89, 0x13, 0x72, 0xBB, + 0xCA, 0xE7, 0xD7, 0x76, 0x88, 0xDE, 0xD6, 0x0B, 0x52, 0x6C, 0x04, 0xC9, 0xBF, 0x0A, 0x7D, 0x96, 0x56, 0x81, 0x90, 0x4D, 0xAC, 0x03, 0x79, 0x1F, 0x08, 0xB0, 0x71, 0xF0, 0xEE, 0x5B, 0xAB, 0xA1, + 0xC4, 0x6B, 0x15, 0x61, 0x75, 0x6E, 0x58, 0x9C, 0x33, 0x7B, 0xAB, 0x4F, 0x2B, 0x75, 0xAE, 0x3B, 0xF6, 0xE7, 0x74, 0x3F, 0x6C, 0xEE, 0x5F, 0x09, 0x93, 0xE7, 0x18, 0xC9, 0x58, 0x4D, 0x47, 0xEA, + 0xD4, 0xC9, 0x61, 0xAE, 0x96, 0xF6, 0xD6, 0x02, 0xA5, 0x06, 0xA2, 0xA4, 0xC0, 0xF5, 0x7E, 0x88, 0x1D, 0x51, 0xDC, 0x24, 0xF2, 0x77, 0xEB, 0xA9, 0xCC, 0x3C, 0x6F, 0x23, 0x58, 0x29, 0xB5, 0xBA, + 0x87, 0xC2, 0x1F, 0x12, 0x32, 0x1C, 0xEE, 0x8B, 0x6E, 0xE9, 0x08, 0x9B, 0xB5, 0x2C, 0x3A, 0x71, 0xAD, 0x61, 0x12, 0x46, 0xAE, 0xD9, 0x80, 0xC1, 0xB9, 0x47, 0xA6, 0x7C, 0x88, 0xA1, 0x10, 0xA7, + 0xBD, 0x84, 0x49, 0xD0, 0x9C, 0xE3, 0x90, 0x6C, 0x65, 0x35, 0x45, 0x7D, 0x02, 0xF2, 0x32, 0x5C, 0x70, 0xEE, 0x78, 0x63, 0xAE, 0x63, 0x23, 0x0F, 0xC2, 0x3D, 0xEC, 0xA2, 0x99, 0xBB, 0x5B, 0x0E, + 0x4B, 0x1A, 0xE8, 0xE2, 0x40, 0x1D, 0xFB, 0x9D, 0x4B, 0xDD, 0xD0, 0x61, 0x18, 0xBD, 0x15, 0x0F, 0x4B, 0x5C, 0xD3, 0x85, 0xAF, 0xB4, 0xFA, 0xD4, 0xEC, 0xA4, 0x6D, 0x61, 0xBE, 0xCA, 0xB1, 0x1D, + 0x02, 0x70, 0x26, 0x67, 0x33, 0x33, 0xAB, 0x31, 0x4B, 0x9E, 0xF9, 0x1B, 0x7A, 0x7F, 0x94, 0x0B, 0xDA, 0x44, 0x44, 0xAE, 0xFE, 0x37, 0x03, 0x6A, 0x43, 0xF2, 0xB6, 0x8D, 0x0D, 0xFF, 0xD7, 0xAF, + 0x33, 0xA3, 0x63, 0x0F, 0xDB, 0x32, 0x5A, 0x74, 0xDA, 0x7B, 0x09, 0x0F, 0x94, 0x9D, 0x06, 0x4B, 0xF7, 0x45, 0xB8, 0x93, 0x37, 0x15, 0x2B, 0x98, 0x0E, 0x4E, 0x20, 0xCC, 0x23, 0xFF, 0xAF, 0xCC, + 0xBC, 0x7E, 0x95, 0x77, 0x04, 0xE9, 0x4B, 0xE7, 0xF3, 0xE8, 0x5F, 0x7F, 0xE8, 0x49, 0x6F, 0xD5, 0xAA, 0xB9, 0x67, 0xB2, 0x7C, 0x3F, 0x17, 0x3E, 0x26, 0x26, 0x80, 0xD0, 0x44, 0x08, 0x85, 0xE6, + 0xC0, 0xB2, 0xAA, 0xB0, 0x9A, 0xB8, 0x1F, 0x6D, 0xE5, 0xB2, 0x2D, 0x17, 0xD5, 0xA2, 0x11, 0x97, 0xD6, 0x98, 0x93, 0xBE, 0xED, 0x51, 0x83, 0x4E, 0x2D, 0x7E, 0x3D, 0xAF, 0xF0, 0x4C, 0xF8, 0x4A, + 0xA9, 0xC7, 0x79, 0x6E, 0xBB, 0x6A, 0xE2, 0x06, 0xC4, 0xE1, 0x66, 0x25, 0xFD, 0xFD, 0x61, 0x39, 0x85, 0x05, 0x48, 0x06, 0x26, 0x7C, 0xD6, 0x9B, 0xFA, 0x8F, 0x5D, 0xD6, 0x0F, 0x4F, 0x21, 0x94, + 0x12, 0xDF, 0x2B, 0xAB, 0xC9, 0x56, 0x41, 0xAE, 0x15, 0x54, 0x87, 0xFA, 0xF4, 0x13, 0x33, 0xF5, 0xE5, 0x1B, 0xEF, 0xC2, 0xF9, 0x63, 0xE6, 0x2B, 0x74, 0x8B, 0x3D, 0x9C, 0x20, 0x20, 0x66, 0xD1, + 0xEC, 0xBA, 0xB6, 0x03, 0x21, 0x79, 0x10, 0x58, 0x9B, 0xB9, 0x69, 0x55, 0x21, 0xA5, 0xC5, 0x2F, 0x12, 0x38, 0x2F, 0x0D, 0xE3, 0x24, 0x3F, 0x9E, 0x92, 0xED, 0x60, 0x53, 0x12, 0x63, 0x7D, 0xCC, + 0xE5, 0xAD, 0x80, 0x7D, 0xA0, 0xC9, 0x2E, 0x99, 0x32, 0x52, 0x05, 0x20, 0x41, 0xC7, 0xB6, 0x8F, 0x4E, 0xB1, 0xBB, 0xB7, 0x08, 0x5A, 0x5B, 0x02, 0x04, 0x77, 0x98, 0x92, 0x30, 0xCB, 0xA8, 0x9F, + 0x96, 0x6D, 0x34, 0x97, 0xC4, 0x04, 0x3D, 0x05, 0x6F, 0x79, 0x7E, 0xA0, 0xB4, 0x8E, 0x24, 0x7C, 0xAB, 0xBC, 0x7E, 0x59, 0x73, 0x07, 0xDA, 0x60, 0x5A, 0x00, 0x81, 0x45, 0x45, 0x51, 0xC8, 0x96, + 0xAB, 0x4E, 0xE1, 0x34, 0x6B, 0x90, 0x4E, 0x35, 0x8A, 0x58, 0xCA, 0x2F, 0x7B, 0x93, 0xDA, 0x32, 0x9D, 0x08, 0x0A, 0x49, 0xDC, 0xF9, 0xD2, 0xC9, 0xD1, 0xBB, 0xD6, 0xBA, 0x82, 0x6C, 0xA7, 0x13, + 0x3A, 0xB2, 0xDF, 0x61, 0xD7, 0x13, 0x16, 0xEB, 0xDD, 0xED, 0x88, 0x2E, 0x49, 0x83, 0xB7, 0x67, 0x46, 0xF7, 0x14, 0x36, 0xD2, 0xD7, 0xC1, 0x4D, 0x94, 0x34, 0x71, 0x70, 0xEE, 0x00, 0x15, 0x54, + 0x00, 0x28, 0x1B, 0xD3, 0xC6, 0xBF, 0xE5, 0xEC, 0xBF, 0x69, 0xDE, 0xA0, 0x59, 0x01, 0x63, 0xE3, 0xA2, 0x97, 0x10, 0xC4, 0x10, 0x7A, 0x08, 0xD4, 0xDD, 0x30, 0xFD, 0x6E, 0x05, 0x0E, 0xA1, 0xE9, + 0xE3, 0xF3, 0xBA, 0xCD, 0x74, 0x10, 0x35, 0xE3, 0x47, 0x18, 0xAF, 0xA9, 0xA9, 0xC8, 0xAB, 0x19, 0xEA, 0x9C, 0xD8, 0x75, 0x11, 0xCC, 0x59, 0xCC, 0x60, 0x1B, 0xC6, 0x3B, 0x82, 0x0F, 0xD0, 0x96, + 0x87, 0x1F, 0x95, 0x26, 0x34, 0xA2, 0xA3, 0x78, 0x87, 0x83, 0xAA, 0xE7, 0x6D, 0xA2, 0x05, 0xB1, 0xEB, 0x5E, 0x94, 0x42, 0x16, 0x19, 0xFF, 0x47, 0x52, 0x5F, 0x05, 0x62, 0xE4, 0xA3, 0x63, 0x3A, + 0xC7, 0xC4, 0x01, 0x7D, 0xA2, 0xC8, 0x13, 0x07, 0xBD, 0xBD, 0x74, 0xB2, 0xD9, 0x16, 0x1E, 0x99, 0xC1, 0x68, 0x6A, 0x9A, 0xB1, 0xC9, 0x44, 0x1B, 0x0D, 0x35, 0xC1, 0xCE, 0x7E, 0x9A, 0x62, 0x88, + 0x28, 0x92, 0x85, 0x02, 0x33, 0x20, 0x88, 0x9B, 0x63, 0x9E, 0xB9, 0xCD, 0x0A, 0x56, 0x92, 0x93, 0xE3, 0x67, 0xC2, 0xBD, 0x1F, 0xEA, 0x68, 0x7F, 0x45, 0x1B, 0x3D, 0xA8, 0x80, 0x9A, 0x77, 0xCA, + 0x31, 0x9D, 0xFC, 0xFF, 0xBA, 0xD4, 0x27, 0x24, 0xF2, 0xE0, 0x67, 0xCB, 0x3A, 0x85, 0xE7, 0x23, 0xCD, 0xD0, 0xEF, 0xC6, 0xB4, 0xC9, 0x7B, 0x5A, 0x13, 0x6B, 0xBE, 0xFC, 0xB6, 0xF1, 0x34, 0x59, + 0x2C, 0xED, 0xDD, 0x6A, 0xFC, 0x98, 0x30, 0x36, 0x5D, 0x75, 0xF7, 0x5A, 0x27, 0xCA, 0xC7, 0x22, 0x56, 0x07, 0x8E, 0xD0, 0x20, 0xA4, 0x49, 0x30, 0xDE, 0x9C, 0x35, 0xCE, 0x96, 0xE1, 0x54, 0x4E, + 0xE9, 0x85, 0x1B, 0xE6, 0x78, 0x48, 0x2A, 0x32, 0x7C, 0xFA, 0x37, 0xA9, 0x13, 0xE0, 0x45, 0xC8, 0xC2, 0x63, 0xD9, 0xB2, 0x5E, 0xAE, 0x21, 0xA2, 0x66, 0x4A, 0xF9, 0x43, 0x03, 0x95, 0x16, 0x3F, + 0x04, 0x56, 0xD1, 0xA5, 0x18, 0xF6, 0x09, 0x7C, 0x96, 0xDB, 0x8F, 0x50, 0x5F, 0x34, 0x40, 0xA6, 0xC8, 0xCC, 0x31, 0xB5, 0x95, 0xAC, 0xFE, 0x9A, 0xA9, 0xCC, 0x1C, 0xCF, 0xF9, 0xFD, 0xA6, 0x56, + 0xBC, 0xDB, 0x5E, 0xEB, 0x57, 0xF4, 0x1E, 0x94, 0x67, 0xC6, 0x43, 0xBA, 0x62, 0x79, 0xE5, 0x41, 0xE8, 0x6C, 0x91, 0x07, 0x4E, 0x55, 0xC6, 0x3A, 0xDF, 0x41, 0x51, 0x7C, 0xEA, 0x5A, 0x6F, 0x62, + 0x29, 0xF7, 0x10, 0x16, 0x62, 0xBB, 0x0A, 0xA0, 0xCE, 0xAB, 0x2B, 0x7F, 0x62, 0x11, 0x96, 0xC7, 0xA7, 0x7B, 0xB3, 0x27, 0xC7, 0x68, 0xC4, 0x3D, 0x06, 0x9D, 0x71, 0xC3, 0x2C, 0x71, 0x2C, 0x83, + 0x1D, 0x68, 0x50, 0xE6, 0xEB, 0x79, 0x3D, 0x7D, 0xEB, 0x08, 0xDE, 0x7A, 0x70, 0x4B, 0x38, 0x6D, 0xFD, 0x2B, 0x30, 0x72, 0xC2, 0x6B, 0x89, 0xDF, 0x8D, 0x07, 0x2B, 0x3E, 0x9F, 0x56, 0x96, 0xA0, + 0x73, 0x2E, 0x21, 0x5D, 0xF6, 0xDE, 0x47, 0x5D, 0x3A, 0x69, 0xF1, 0x11, 0x2F, 0x8B, 0x6B, 0x8E, 0xE7, 0x6B, 0x73, 0x9C, 0x92, 0x76, 0xD9, 0xEE, 0x78, 0x17, 0xD9, 0x89, 0xAA, 0x07, 0x90, 0xD4, + 0x6F, 0x8B, 0xE9, 0xBC, 0xF8, 0xA9, 0xDE, 0x83, 0xD3, 0xF3, 0xC3, 0x02, 0xA8, 0xAA, 0xBE, 0xE5, 0xC8, 0xFE, 0xBC, 0x2A, 0xDC, 0x70, 0x6F, 0xC0, 0xEA, 0x55, 0xCD, 0x6F, 0x38, 0x37, 0x74, 0xF9, + 0x55, 0xFE, 0xC7, 0x0A, 0x5F, 0x83, 0x80, 0x74, 0xDC, 0xB7, 0x31, 0x53, 0x2C, 0x94, 0x9C, 0x88, 0x84, 0xE9, 0x5F, 0xDE, 0xCE, 0x3A, 0x7D, 0x9F, 0x7E, 0xA2, 0x1A, 0xC5, 0xA8, 0xAC, 0xDF, 0xAA, + 0x89, 0x68, 0x1E, 0x95, 0x01, 0x4D, 0x5A, 0x23, 0x44, 0x31, 0x5B, 0xF8, 0xB3, 0xFF, 0x97, 0x12, 0xA0, 0x9A, 0x8F, 0xDE, 0xB8, 0x29, 0x4C, 0x25, 0x7D, 0x16, 0xCC, 0xEF, 0xAA, 0x78, 0xDD, 0x0F, + 0x5D, 0xFF, 0xE0, 0x49, 0xCE, 0x2B, 0x8A, 0xC7, 0xE1, 0x60, 0x02, 0xED, 0x1E, 0x32, 0x8C, 0x62, 0x86, 0xA1, 0x67, 0x4A, 0x5C, 0x06, 0xF6, 0x28, 0x37, 0xAA, 0xF3, 0xEE, 0xFF, 0xFC, 0x11, 0x46, + 0x94, 0x7A, 0x63, 0x0D, 0x82, 0x44, 0xAA, 0x72, 0x89, 0x8D, 0xFE, 0x5B, 0x94, 0x78, 0x63, 0x70, 0x64, 0x8A, 0x13, 0xF0, 0xE1, 0x6D, 0x50, 0x27, 0x77, 0xEB, 0x8D, 0xF9, 0x62, 0xFC, 0x86, 0x3C, + 0x77, 0xC1, 0x59, 0xBF, 0x64, 0xCC, 0x2A, 0x47, 0xCA, 0xF6, 0xB2, 0x12, 0xCB, 0xC6, 0x14, 0x2B, 0x5C, 0x9F, 0x5B, 0xFF, 0xE2, 0xDD, 0x3B, 0xB1, 0xF8, 0x63, 0x23, 0x10, 0x74, 0x82, 0x96, 0xBB, + 0x81, 0xB3, 0x62, 0xB7, 0xE4, 0x56, 0xEE, 0xE8, 0xDF, 0x29, 0x55, 0xFC, 0xDC, 0x04, 0xE5, 0x5D, 0x25, 0x16, 0xA8, 0x28, 0x07, 0x12, 0xCA, 0x5B, 0x60, 0xEA, 0x90, 0x7D, 0x51, 0xB2, 0xFA, 0x72, + 0xF9, 0xC7, 0x3D, 0xA7, 0xFE, 0x2C, 0x25, 0x98, 0x8F, 0x5B, 0xE1, 0xB8, 0x23, 0x68, 0x25, 0xC8, 0x3A, 0x02, 0x38, 0x22, 0x39, 0x40, 0x2A, 0x29, 0x4E, 0xA4, 0xBE, 0x31, 0xA1, 0x7D, 0xBD, 0x31, + 0xBA, 0x1B, 0xFF, 0xF8, 0x04, 0xCC, 0x78, 0x2F, 0xED, 0x78, 0x95, 0x09, 0x7F, 0x58, 0x3D, 0xD1, 0x3A, 0xCC, 0x85, 0x49, 0x1B, 0xDD, 0x12, 0x3F, 0xE0, 0x2C, 0x14, 0x12, 0xE3, 0x42, 0x61, 0x7D, + 0x9C, 0x26, 0xB8, 0xD9, 0x87, 0x7C, 0xAD, 0x5A, 0x72, 0xD2, 0x32, 0x80, 0xB5, 0x27, 0x61, 0x47, 0xA7, 0x25, 0x84, 0xDA, 0xE6, 0x17, 0x23, 0x15, 0x8B, 0x9A, 0x54, 0x79, 0xD6, 0x6B, 0x6D, 0x8A, + 0x6C, 0x4D, 0xB0, 0xF2, 0xE7, 0x1E, 0xDD, 0x46, 0x58, 0x85, 0xC3, 0x3A, 0x69, 0xA8, 0xA7, 0x4E, 0x78, 0x16, 0x08, 0xF0, 0x64, 0x16, 0x86, 0x6D, 0x19, 0x6B, 0x69, 0x5E, 0x70, 0xA4, 0x3B, 0x7D, + 0xEA, 0xBE, 0x8C, 0x00, 0x0D, 0x79, 0xEE, 0x16, 0x03, 0xD4, 0x7C, 0x45, 0xCC, 0xB8, 0x5B, 0xBF, 0x79, 0x2D, 0x59, 0x14, 0x6F, 0xA3, 0x22, 0x86, 0x97, 0x6F, 0xF5, 0x91, 0x72, 0x62, 0x96, 0x38, + 0xE1, 0xA0, 0x70, 0xCB, 0x0F, 0x0E, 0xCB, 0xF8, 0x09, 0xF9, 0xF5, 0xB8, 0x73, 0xFB, 0xEF, 0x96, 0x87, 0x4F, 0xCD, 0xED, 0x58, 0xA2, 0xC0, 0xA4, 0x99, 0x06, 0xD9, 0x09, 0x1D, 0x29, 0xB2, 0x1D, + 0x0A, 0x7B, 0x89, 0x94, 0x52, 0x5D, 0x08, 0x88, 0x74, 0x8F, 0xB7, 0xDE, 0xE1, 0x60, 0xF2, 0xFC, 0xC7, 0x89, 0x52, 0xBB, 0x57, 0xBE, 0x4D, 0x36, 0x68, 0x5B, 0xE4, 0xF2, 0xB1, 0x45, 0xBC, 0xAC, + 0x40, 0xE0, 0xDB, 0x30, 0x60, 0x87, 0x2D, 0x81, 0x76, 0x63, 0x91, 0xD4, 0xEC, 0x0B, 0x04, 0x60, 0x9F, 0x4F, 0x2D, 0xA2, 0x28, 0x94, 0x15, 0x45, 0x8D, 0x5F, 0x15, 0x22, 0x3C, 0x8E, 0x91, 0x11, + 0x88, 0xC7, 0x82, 0x5F, 0x52, 0xA0, 0xA3, 0xA2, 0xC2, 0xCA, 0x8B, 0x62, 0xA7, 0x4B, 0x03, 0x71, 0x59, 0xE5, 0x4D, 0x99, 0x73, 0xC8, 0x00, 0x54, 0x3D, 0x2F, 0x6C, 0x4C, 0x0D, 0x9E, 0x3B, 0x09, + 0x39, 0xC1, 0xC1, 0x68, 0x05, 0xE5, 0x79, 0x46, 0x95, 0x49, 0x9C, 0xE0, 0x13, 0xCF, 0xB9, 0xB0, 0xEA, 0xEE, 0xD8, 0xDD, + }, + .spki_len = 2374, + .spki = { + 0x30, 0x82, 0x09, 0x42, 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0B, 0x01, 0x08, 0x07, 0x05, 0x00, 0x03, 0x82, 0x09, 0x2D, 0x00, 0x30, 0x82, 0x09, 0x28, 0x03, 0x21, + 0x00, 0x7C, 0x99, 0x35, 0xA0, 0xB0, 0x76, 0x94, 0xAA, 0x0C, 0x6D, 0x10, 0xE4, 0xDB, 0x6B, 0x1A, 0xDD, 0x2F, 0xD8, 0x1A, 0x25, 0xCC, 0xB1, 0x48, 0x03, 0x2D, 0xCD, 0x73, 0x99, 0x36, 0x73, 0x7F, + 0x2D, 0x03, 0x82, 0x09, 0x01, 0x00, 0x94, 0x06, 0xE4, 0xDC, 0xE8, 0x12, 0xBE, 0x92, 0xE1, 0x53, 0xE0, 0x75, 0x2C, 0xFE, 0x26, 0xC1, 0x12, 0x7E, 0x9C, 0x80, 0xC8, 0x11, 0x3E, 0x12, 0x16, 0x95, + 0xF9, 0x01, 0x4E, 0x03, 0xFF, 0xF1, 0xFD, 0x7B, 0xE3, 0xB0, 0xF4, 0x0E, 0xEE, 0x5B, 0x02, 0xF5, 0x60, 0x1E, 0x2F, 0xC3, 0xAF, 0xF0, 0xCD, 0xF7, 0xE7, 0xE7, 0x34, 0x99, 0x9C, 0x7F, 0xC4, 0xEB, + 0x9D, 0xDA, 0x81, 0x8C, 0x52, 0x06, 0x93, 0xFE, 0x38, 0xE4, 0x49, 0xBE, 0x4C, 0xCF, 0x03, 0xFE, 0xA1, 0x72, 0x8E, 0x4C, 0xCA, 0x64, 0xFD, 0x11, 0x0B, 0xFC, 0x8E, 0xC9, 0xCB, 0x79, 0x50, 0x3B, + 0xD5, 0x53, 0xF5, 0x89, 0x9A, 0x2F, 0x63, 0x16, 0x5D, 0x19, 0x32, 0x72, 0x7D, 0xB7, 0x44, 0x72, 0x65, 0xF7, 0x96, 0xF4, 0xFD, 0xBC, 0xFE, 0xA6, 0xF4, 0x05, 0x9E, 0x88, 0x34, 0x34, 0xC7, 0x98, + 0xB8, 0x68, 0xF9, 0x86, 0x60, 0x5D, 0x4D, 0x03, 0xD3, 0x04, 0xB6, 0x77, 0xE3, 0x0F, 0xF7, 0xD7, 0x83, 0x0A, 0xDD, 0x06, 0x65, 0x2B, 0xCC, 0x1B, 0xF0, 0x4D, 0x33, 0xDF, 0xFE, 0xFC, 0xEF, 0x63, + 0x4A, 0xF5, 0xBA, 0xE0, 0xD5, 0xC6, 0xBA, 0xB6, 0xC5, 0x64, 0xF1, 0x95, 0x20, 0x82, 0xAA, 0x38, 0x25, 0x53, 0x20, 0x01, 0x9C, 0xBC, 0x8E, 0xCA, 0x07, 0x3D, 0x80, 0xAF, 0x0A, 0x59, 0x6E, 0x4D, + 0x33, 0xAD, 0x73, 0xB4, 0xF1, 0xED, 0xD4, 0x20, 0xE0, 0x90, 0x0B, 0xED, 0x47, 0x49, 0x5A, 0x88, 0x62, 0xD4, 0xA9, 0xCD, 0xDE, 0xD0, 0xDE, 0xA7, 0x74, 0xCD, 0xE0, 0x23, 0x8C, 0x71, 0x2B, 0x8A, + 0xA9, 0x82, 0x47, 0x56, 0x66, 0x0D, 0x2B, 0x34, 0xE4, 0x7E, 0x4B, 0x59, 0x42, 0x5F, 0x17, 0xA9, 0x60, 0x8D, 0xAD, 0x38, 0x28, 0xEC, 0x9D, 0x8A, 0xDB, 0x5D, 0xD3, 0x8C, 0x7D, 0x53, 0xDD, 0xA6, + 0xDA, 0xC7, 0x4D, 0x3F, 0xD0, 0x3C, 0x00, 0xB5, 0x9E, 0xE9, 0xA0, 0xE5, 0x27, 0x6E, 0x3E, 0x75, 0xD0, 0x13, 0x61, 0x01, 0x66, 0x49, 0x1D, 0x87, 0x3A, 0x7D, 0xA2, 0xC9, 0xFD, 0xA3, 0x60, 0xA6, + 0x47, 0x73, 0x25, 0x00, 0x58, 0x41, 0x8F, 0xA7, 0x62, 0x63, 0x2D, 0xCB, 0x12, 0x63, 0x85, 0x27, 0x32, 0x60, 0x02, 0x18, 0x67, 0x53, 0xE6, 0xB5, 0xD3, 0x31, 0xE5, 0x64, 0x23, 0xC9, 0x70, 0x9D, + 0x34, 0x9C, 0x69, 0x5A, 0x32, 0x8A, 0x56, 0x2B, 0x13, 0x9A, 0xF5, 0x98, 0xF8, 0x5D, 0xCB, 0x35, 0x98, 0x40, 0x7D, 0x82, 0xF8, 0x49, 0xC2, 0x9A, 0x87, 0xDC, 0x41, 0xFA, 0xA7, 0x69, 0x8F, 0xAC, + 0x7F, 0x20, 0x4D, 0x70, 0xD0, 0x7D, 0x4A, 0xDC, 0x1D, 0x68, 0xFB, 0x46, 0x08, 0x63, 0xBB, 0x00, 0x2F, 0x3A, 0x23, 0x57, 0xCB, 0x65, 0xFB, 0x4B, 0x03, 0xBA, 0xB6, 0x8D, 0xB9, 0xB1, 0x1A, 0x09, + 0xC9, 0x02, 0xE8, 0x12, 0x95, 0x91, 0x54, 0x16, 0xB4, 0x51, 0xD8, 0xE5, 0xFB, 0xF7, 0x81, 0x33, 0xBE, 0xD2, 0x81, 0x81, 0x37, 0x17, 0xE3, 0x74, 0xC5, 0xB4, 0x15, 0xE7, 0x77, 0x3F, 0x95, 0xD8, + 0x3D, 0x8B, 0xF9, 0x7D, 0x4A, 0xC4, 0x5E, 0xAC, 0x28, 0x1E, 0x50, 0x89, 0x69, 0x32, 0xF7, 0xEE, 0xA4, 0x83, 0xE6, 0x98, 0xED, 0xD6, 0x07, 0xC3, 0xFF, 0xDD, 0xD3, 0x4C, 0x56, 0x67, 0x03, 0x28, + 0xEB, 0xA5, 0xE1, 0xEB, 0x24, 0x9B, 0x8E, 0x26, 0x85, 0x38, 0xBF, 0x4C, 0xF3, 0x43, 0x2E, 0xD5, 0xA9, 0x33, 0xB8, 0x2E, 0x6C, 0x0E, 0x96, 0x0D, 0xE1, 0x8A, 0x20, 0x9F, 0xA3, 0x90, 0x96, 0x93, + 0x87, 0x88, 0x4D, 0xAD, 0x8D, 0x8E, 0xE7, 0xE6, 0x0A, 0x89, 0x69, 0x90, 0x62, 0x16, 0x2F, 0x90, 0xBB, 0x28, 0xE4, 0xCC, 0xBA, 0x1A, 0x5F, 0x52, 0x6D, 0xE9, 0xCF, 0x7F, 0xEF, 0xEC, 0x7A, 0x77, + 0xDD, 0xA0, 0x7C, 0xD7, 0x00, 0x09, 0xE4, 0x8E, 0xBF, 0x8E, 0xDD, 0x9B, 0x34, 0x87, 0x26, 0xA9, 0x37, 0xE1, 0x4F, 0xF5, 0xEB, 0x6E, 0x79, 0xE3, 0xDB, 0x1B, 0x60, 0xD7, 0x0A, 0x73, 0x05, 0x11, + 0x15, 0x4A, 0x8A, 0xB8, 0x75, 0xF8, 0x6D, 0xEB, 0xCB, 0x9D, 0x79, 0x0F, 0xC4, 0x32, 0x84, 0x4E, 0x90, 0x3C, 0x8B, 0xD9, 0xFD, 0xB2, 0x8F, 0x99, 0x88, 0xDF, 0xAE, 0xA5, 0x56, 0xE9, 0x20, 0xE5, + 0x79, 0x25, 0x47, 0xAE, 0xA7, 0xA4, 0x5B, 0x4C, 0x7E, 0x68, 0x41, 0x61, 0x1E, 0x33, 0x06, 0x4E, 0x5C, 0xB5, 0x9B, 0xBA, 0xEC, 0xA6, 0x9E, 0x38, 0xA0, 0x99, 0x94, 0xAE, 0xEA, 0x3D, 0x10, 0xF6, + 0xFC, 0x53, 0xF6, 0x43, 0x56, 0x2F, 0xA0, 0x0A, 0x34, 0x12, 0xD4, 0xAF, 0xF8, 0x01, 0xD4, 0x8D, 0x0C, 0x58, 0xBA, 0x05, 0x5A, 0x42, 0xCD, 0xF6, 0xB8, 0xF1, 0x86, 0x16, 0x99, 0xEF, 0xD9, 0xAD, + 0x9D, 0xF4, 0xCB, 0xB9, 0x88, 0xE7, 0x22, 0x17, 0x12, 0xBB, 0x42, 0xA4, 0x3B, 0xE8, 0x32, 0x25, 0x09, 0x11, 0x1D, 0x3A, 0x8E, 0xBC, 0x97, 0xFA, 0xEB, 0xF9, 0xF8, 0x5D, 0x69, 0x20, 0x76, 0x5A, + 0x18, 0x2A, 0xD9, 0xC4, 0x54, 0x27, 0x99, 0x31, 0x70, 0x5E, 0xA2, 0x90, 0x3F, 0x6E, 0x18, 0x7D, 0x2A, 0xF6, 0xA5, 0xE4, 0xA8, 0x30, 0x54, 0x16, 0x8A, 0xA6, 0xA6, 0xF1, 0x27, 0xC8, 0xCE, 0x0C, + 0x56, 0xA2, 0xEF, 0x67, 0xDC, 0x1C, 0xD9, 0xB2, 0x2A, 0x51, 0x39, 0xDA, 0xC1, 0x92, 0xFF, 0xC5, 0x3A, 0x13, 0xEC, 0x52, 0xA3, 0x22, 0x07, 0xA9, 0x6A, 0x4F, 0xED, 0xB1, 0x20, 0x55, 0xFF, 0xDD, + 0xBE, 0xE6, 0xAE, 0xF0, 0x72, 0xF7, 0x5D, 0xB7, 0xC6, 0xCD, 0x37, 0xB2, 0x58, 0x9D, 0xC0, 0x0F, 0xBE, 0xF1, 0x33, 0x3E, 0xB1, 0x13, 0xC8, 0x22, 0x1B, 0xF8, 0x74, 0x0F, 0xD7, 0xBF, 0x7F, 0x39, + 0xA5, 0x7E, 0x4A, 0xE2, 0xCE, 0x86, 0xE0, 0xE8, 0xB4, 0xE9, 0x21, 0x4D, 0x67, 0x21, 0x46, 0xED, 0xE9, 0x85, 0x87, 0x15, 0x71, 0x56, 0x5E, 0x9F, 0x59, 0xCD, 0xA5, 0x92, 0x22, 0xAC, 0x9C, 0x6C, + 0x00, 0xD5, 0xA7, 0xC9, 0xD8, 0xA3, 0xE5, 0x46, 0xDE, 0xC8, 0x3C, 0x65, 0x54, 0xEA, 0x89, 0x13, 0x72, 0xBB, 0xCA, 0xE7, 0xD7, 0x76, 0x88, 0xDE, 0xD6, 0x0B, 0x52, 0x6C, 0x04, 0xC9, 0xBF, 0x0A, + 0x7D, 0x96, 0x56, 0x81, 0x90, 0x4D, 0xAC, 0x03, 0x79, 0x1F, 0x08, 0xB0, 0x71, 0xF0, 0xEE, 0x5B, 0xAB, 0xA1, 0xC4, 0x6B, 0x15, 0x61, 0x75, 0x6E, 0x58, 0x9C, 0x33, 0x7B, 0xAB, 0x4F, 0x2B, 0x75, + 0xAE, 0x3B, 0xF6, 0xE7, 0x74, 0x3F, 0x6C, 0xEE, 0x5F, 0x09, 0x93, 0xE7, 0x18, 0xC9, 0x58, 0x4D, 0x47, 0xEA, 0xD4, 0xC9, 0x61, 0xAE, 0x96, 0xF6, 0xD6, 0x02, 0xA5, 0x06, 0xA2, 0xA4, 0xC0, 0xF5, + 0x7E, 0x88, 0x1D, 0x51, 0xDC, 0x24, 0xF2, 0x77, 0xEB, 0xA9, 0xCC, 0x3C, 0x6F, 0x23, 0x58, 0x29, 0xB5, 0xBA, 0x87, 0xC2, 0x1F, 0x12, 0x32, 0x1C, 0xEE, 0x8B, 0x6E, 0xE9, 0x08, 0x9B, 0xB5, 0x2C, + 0x3A, 0x71, 0xAD, 0x61, 0x12, 0x46, 0xAE, 0xD9, 0x80, 0xC1, 0xB9, 0x47, 0xA6, 0x7C, 0x88, 0xA1, 0x10, 0xA7, 0xBD, 0x84, 0x49, 0xD0, 0x9C, 0xE3, 0x90, 0x6C, 0x65, 0x35, 0x45, 0x7D, 0x02, 0xF2, + 0x32, 0x5C, 0x70, 0xEE, 0x78, 0x63, 0xAE, 0x63, 0x23, 0x0F, 0xC2, 0x3D, 0xEC, 0xA2, 0x99, 0xBB, 0x5B, 0x0E, 0x4B, 0x1A, 0xE8, 0xE2, 0x40, 0x1D, 0xFB, 0x9D, 0x4B, 0xDD, 0xD0, 0x61, 0x18, 0xBD, + 0x15, 0x0F, 0x4B, 0x5C, 0xD3, 0x85, 0xAF, 0xB4, 0xFA, 0xD4, 0xEC, 0xA4, 0x6D, 0x61, 0xBE, 0xCA, 0xB1, 0x1D, 0x02, 0x70, 0x26, 0x67, 0x33, 0x33, 0xAB, 0x31, 0x4B, 0x9E, 0xF9, 0x1B, 0x7A, 0x7F, + 0x94, 0x0B, 0xDA, 0x44, 0x44, 0xAE, 0xFE, 0x37, 0x03, 0x6A, 0x43, 0xF2, 0xB6, 0x8D, 0x0D, 0xFF, 0xD7, 0xAF, 0x33, 0xA3, 0x63, 0x0F, 0xDB, 0x32, 0x5A, 0x74, 0xDA, 0x7B, 0x09, 0x0F, 0x94, 0x9D, + 0x06, 0x4B, 0xF7, 0x45, 0xB8, 0x93, 0x37, 0x15, 0x2B, 0x98, 0x0E, 0x4E, 0x20, 0xCC, 0x23, 0xFF, 0xAF, 0xCC, 0xBC, 0x7E, 0x95, 0x77, 0x04, 0xE9, 0x4B, 0xE7, 0xF3, 0xE8, 0x5F, 0x7F, 0xE8, 0x49, + 0x6F, 0xD5, 0xAA, 0xB9, 0x67, 0xB2, 0x7C, 0x3F, 0x17, 0x3E, 0x26, 0x26, 0x80, 0xD0, 0x44, 0x08, 0x85, 0xE6, 0xC0, 0xB2, 0xAA, 0xB0, 0x9A, 0xB8, 0x1F, 0x6D, 0xE5, 0xB2, 0x2D, 0x17, 0xD5, 0xA2, + 0x11, 0x97, 0xD6, 0x98, 0x93, 0xBE, 0xED, 0x51, 0x83, 0x4E, 0x2D, 0x7E, 0x3D, 0xAF, 0xF0, 0x4C, 0xF8, 0x4A, 0xA9, 0xC7, 0x79, 0x6E, 0xBB, 0x6A, 0xE2, 0x06, 0xC4, 0xE1, 0x66, 0x25, 0xFD, 0xFD, + 0x61, 0x39, 0x85, 0x05, 0x48, 0x06, 0x26, 0x7C, 0xD6, 0x9B, 0xFA, 0x8F, 0x5D, 0xD6, 0x0F, 0x4F, 0x21, 0x94, 0x12, 0xDF, 0x2B, 0xAB, 0xC9, 0x56, 0x41, 0xAE, 0x15, 0x54, 0x87, 0xFA, 0xF4, 0x13, + 0x33, 0xF5, 0xE5, 0x1B, 0xEF, 0xC2, 0xF9, 0x63, 0xE6, 0x2B, 0x74, 0x8B, 0x3D, 0x9C, 0x20, 0x20, 0x66, 0xD1, 0xEC, 0xBA, 0xB6, 0x03, 0x21, 0x79, 0x10, 0x58, 0x9B, 0xB9, 0x69, 0x55, 0x21, 0xA5, + 0xC5, 0x2F, 0x12, 0x38, 0x2F, 0x0D, 0xE3, 0x24, 0x3F, 0x9E, 0x92, 0xED, 0x60, 0x53, 0x12, 0x63, 0x7D, 0xCC, 0xE5, 0xAD, 0x80, 0x7D, 0xA0, 0xC9, 0x2E, 0x99, 0x32, 0x52, 0x05, 0x20, 0x41, 0xC7, + 0xB6, 0x8F, 0x4E, 0xB1, 0xBB, 0xB7, 0x08, 0x5A, 0x5B, 0x02, 0x04, 0x77, 0x98, 0x92, 0x30, 0xCB, 0xA8, 0x9F, 0x96, 0x6D, 0x34, 0x97, 0xC4, 0x04, 0x3D, 0x05, 0x6F, 0x79, 0x7E, 0xA0, 0xB4, 0x8E, + 0x24, 0x7C, 0xAB, 0xBC, 0x7E, 0x59, 0x73, 0x07, 0xDA, 0x60, 0x5A, 0x00, 0x81, 0x45, 0x45, 0x51, 0xC8, 0x96, 0xAB, 0x4E, 0xE1, 0x34, 0x6B, 0x90, 0x4E, 0x35, 0x8A, 0x58, 0xCA, 0x2F, 0x7B, 0x93, + 0xDA, 0x32, 0x9D, 0x08, 0x0A, 0x49, 0xDC, 0xF9, 0xD2, 0xC9, 0xD1, 0xBB, 0xD6, 0xBA, 0x82, 0x6C, 0xA7, 0x13, 0x3A, 0xB2, 0xDF, 0x61, 0xD7, 0x13, 0x16, 0xEB, 0xDD, 0xED, 0x88, 0x2E, 0x49, 0x83, + 0xB7, 0x67, 0x46, 0xF7, 0x14, 0x36, 0xD2, 0xD7, 0xC1, 0x4D, 0x94, 0x34, 0x71, 0x70, 0xEE, 0x00, 0x15, 0x54, 0x00, 0x28, 0x1B, 0xD3, 0xC6, 0xBF, 0xE5, 0xEC, 0xBF, 0x69, 0xDE, 0xA0, 0x59, 0x01, + 0x63, 0xE3, 0xA2, 0x97, 0x10, 0xC4, 0x10, 0x7A, 0x08, 0xD4, 0xDD, 0x30, 0xFD, 0x6E, 0x05, 0x0E, 0xA1, 0xE9, 0xE3, 0xF3, 0xBA, 0xCD, 0x74, 0x10, 0x35, 0xE3, 0x47, 0x18, 0xAF, 0xA9, 0xA9, 0xC8, + 0xAB, 0x19, 0xEA, 0x9C, 0xD8, 0x75, 0x11, 0xCC, 0x59, 0xCC, 0x60, 0x1B, 0xC6, 0x3B, 0x82, 0x0F, 0xD0, 0x96, 0x87, 0x1F, 0x95, 0x26, 0x34, 0xA2, 0xA3, 0x78, 0x87, 0x83, 0xAA, 0xE7, 0x6D, 0xA2, + 0x05, 0xB1, 0xEB, 0x5E, 0x94, 0x42, 0x16, 0x19, 0xFF, 0x47, 0x52, 0x5F, 0x05, 0x62, 0xE4, 0xA3, 0x63, 0x3A, 0xC7, 0xC4, 0x01, 0x7D, 0xA2, 0xC8, 0x13, 0x07, 0xBD, 0xBD, 0x74, 0xB2, 0xD9, 0x16, + 0x1E, 0x99, 0xC1, 0x68, 0x6A, 0x9A, 0xB1, 0xC9, 0x44, 0x1B, 0x0D, 0x35, 0xC1, 0xCE, 0x7E, 0x9A, 0x62, 0x88, 0x28, 0x92, 0x85, 0x02, 0x33, 0x20, 0x88, 0x9B, 0x63, 0x9E, 0xB9, 0xCD, 0x0A, 0x56, + 0x92, 0x93, 0xE3, 0x67, 0xC2, 0xBD, 0x1F, 0xEA, 0x68, 0x7F, 0x45, 0x1B, 0x3D, 0xA8, 0x80, 0x9A, 0x77, 0xCA, 0x31, 0x9D, 0xFC, 0xFF, 0xBA, 0xD4, 0x27, 0x24, 0xF2, 0xE0, 0x67, 0xCB, 0x3A, 0x85, + 0xE7, 0x23, 0xCD, 0xD0, 0xEF, 0xC6, 0xB4, 0xC9, 0x7B, 0x5A, 0x13, 0x6B, 0xBE, 0xFC, 0xB6, 0xF1, 0x34, 0x59, 0x2C, 0xED, 0xDD, 0x6A, 0xFC, 0x98, 0x30, 0x36, 0x5D, 0x75, 0xF7, 0x5A, 0x27, 0xCA, + 0xC7, 0x22, 0x56, 0x07, 0x8E, 0xD0, 0x20, 0xA4, 0x49, 0x30, 0xDE, 0x9C, 0x35, 0xCE, 0x96, 0xE1, 0x54, 0x4E, 0xE9, 0x85, 0x1B, 0xE6, 0x78, 0x48, 0x2A, 0x32, 0x7C, 0xFA, 0x37, 0xA9, 0x13, 0xE0, + 0x45, 0xC8, 0xC2, 0x63, 0xD9, 0xB2, 0x5E, 0xAE, 0x21, 0xA2, 0x66, 0x4A, 0xF9, 0x43, 0x03, 0x95, 0x16, 0x3F, 0x04, 0x56, 0xD1, 0xA5, 0x18, 0xF6, 0x09, 0x7C, 0x96, 0xDB, 0x8F, 0x50, 0x5F, 0x34, + 0x40, 0xA6, 0xC8, 0xCC, 0x31, 0xB5, 0x95, 0xAC, 0xFE, 0x9A, 0xA9, 0xCC, 0x1C, 0xCF, 0xF9, 0xFD, 0xA6, 0x56, 0xBC, 0xDB, 0x5E, 0xEB, 0x57, 0xF4, 0x1E, 0x94, 0x67, 0xC6, 0x43, 0xBA, 0x62, 0x79, + 0xE5, 0x41, 0xE8, 0x6C, 0x91, 0x07, 0x4E, 0x55, 0xC6, 0x3A, 0xDF, 0x41, 0x51, 0x7C, 0xEA, 0x5A, 0x6F, 0x62, 0x29, 0xF7, 0x10, 0x16, 0x62, 0xBB, 0x0A, 0xA0, 0xCE, 0xAB, 0x2B, 0x7F, 0x62, 0x11, + 0x96, 0xC7, 0xA7, 0x7B, 0xB3, 0x27, 0xC7, 0x68, 0xC4, 0x3D, 0x06, 0x9D, 0x71, 0xC3, 0x2C, 0x71, 0x2C, 0x83, 0x1D, 0x68, 0x50, 0xE6, 0xEB, 0x79, 0x3D, 0x7D, 0xEB, 0x08, 0xDE, 0x7A, 0x70, 0x4B, + 0x38, 0x6D, 0xFD, 0x2B, 0x30, 0x72, 0xC2, 0x6B, 0x89, 0xDF, 0x8D, 0x07, 0x2B, 0x3E, 0x9F, 0x56, 0x96, 0xA0, 0x73, 0x2E, 0x21, 0x5D, 0xF6, 0xDE, 0x47, 0x5D, 0x3A, 0x69, 0xF1, 0x11, 0x2F, 0x8B, + 0x6B, 0x8E, 0xE7, 0x6B, 0x73, 0x9C, 0x92, 0x76, 0xD9, 0xEE, 0x78, 0x17, 0xD9, 0x89, 0xAA, 0x07, 0x90, 0xD4, 0x6F, 0x8B, 0xE9, 0xBC, 0xF8, 0xA9, 0xDE, 0x83, 0xD3, 0xF3, 0xC3, 0x02, 0xA8, 0xAA, + 0xBE, 0xE5, 0xC8, 0xFE, 0xBC, 0x2A, 0xDC, 0x70, 0x6F, 0xC0, 0xEA, 0x55, 0xCD, 0x6F, 0x38, 0x37, 0x74, 0xF9, 0x55, 0xFE, 0xC7, 0x0A, 0x5F, 0x83, 0x80, 0x74, 0xDC, 0xB7, 0x31, 0x53, 0x2C, 0x94, + 0x9C, 0x88, 0x84, 0xE9, 0x5F, 0xDE, 0xCE, 0x3A, 0x7D, 0x9F, 0x7E, 0xA2, 0x1A, 0xC5, 0xA8, 0xAC, 0xDF, 0xAA, 0x89, 0x68, 0x1E, 0x95, 0x01, 0x4D, 0x5A, 0x23, 0x44, 0x31, 0x5B, 0xF8, 0xB3, 0xFF, + 0x97, 0x12, 0xA0, 0x9A, 0x8F, 0xDE, 0xB8, 0x29, 0x4C, 0x25, 0x7D, 0x16, 0xCC, 0xEF, 0xAA, 0x78, 0xDD, 0x0F, 0x5D, 0xFF, 0xE0, 0x49, 0xCE, 0x2B, 0x8A, 0xC7, 0xE1, 0x60, 0x02, 0xED, 0x1E, 0x32, + 0x8C, 0x62, 0x86, 0xA1, 0x67, 0x4A, 0x5C, 0x06, 0xF6, 0x28, 0x37, 0xAA, 0xF3, 0xEE, 0xFF, 0xFC, 0x11, 0x46, 0x94, 0x7A, 0x63, 0x0D, 0x82, 0x44, 0xAA, 0x72, 0x89, 0x8D, 0xFE, 0x5B, 0x94, 0x78, + 0x63, 0x70, 0x64, 0x8A, 0x13, 0xF0, 0xE1, 0x6D, 0x50, 0x27, 0x77, 0xEB, 0x8D, 0xF9, 0x62, 0xFC, 0x86, 0x3C, 0x77, 0xC1, 0x59, 0xBF, 0x64, 0xCC, 0x2A, 0x47, 0xCA, 0xF6, 0xB2, 0x12, 0xCB, 0xC6, + 0x14, 0x2B, 0x5C, 0x9F, 0x5B, 0xFF, 0xE2, 0xDD, 0x3B, 0xB1, 0xF8, 0x63, 0x23, 0x10, 0x74, 0x82, 0x96, 0xBB, 0x81, 0xB3, 0x62, 0xB7, 0xE4, 0x56, 0xEE, 0xE8, 0xDF, 0x29, 0x55, 0xFC, 0xDC, 0x04, + 0xE5, 0x5D, 0x25, 0x16, 0xA8, 0x28, 0x07, 0x12, 0xCA, 0x5B, 0x60, 0xEA, 0x90, 0x7D, 0x51, 0xB2, 0xFA, 0x72, 0xF9, 0xC7, 0x3D, 0xA7, 0xFE, 0x2C, 0x25, 0x98, 0x8F, 0x5B, 0xE1, 0xB8, 0x23, 0x68, + 0x25, 0xC8, 0x3A, 0x02, 0x38, 0x22, 0x39, 0x40, 0x2A, 0x29, 0x4E, 0xA4, 0xBE, 0x31, 0xA1, 0x7D, 0xBD, 0x31, 0xBA, 0x1B, 0xFF, 0xF8, 0x04, 0xCC, 0x78, 0x2F, 0xED, 0x78, 0x95, 0x09, 0x7F, 0x58, + 0x3D, 0xD1, 0x3A, 0xCC, 0x85, 0x49, 0x1B, 0xDD, 0x12, 0x3F, 0xE0, 0x2C, 0x14, 0x12, 0xE3, 0x42, 0x61, 0x7D, 0x9C, 0x26, 0xB8, 0xD9, 0x87, 0x7C, 0xAD, 0x5A, 0x72, 0xD2, 0x32, 0x80, 0xB5, 0x27, + 0x61, 0x47, 0xA7, 0x25, 0x84, 0xDA, 0xE6, 0x17, 0x23, 0x15, 0x8B, 0x9A, 0x54, 0x79, 0xD6, 0x6B, 0x6D, 0x8A, 0x6C, 0x4D, 0xB0, 0xF2, 0xE7, 0x1E, 0xDD, 0x46, 0x58, 0x85, 0xC3, 0x3A, 0x69, 0xA8, + 0xA7, 0x4E, 0x78, 0x16, 0x08, 0xF0, 0x64, 0x16, 0x86, 0x6D, 0x19, 0x6B, 0x69, 0x5E, 0x70, 0xA4, 0x3B, 0x7D, 0xEA, 0xBE, 0x8C, 0x00, 0x0D, 0x79, 0xEE, 0x16, 0x03, 0xD4, 0x7C, 0x45, 0xCC, 0xB8, + 0x5B, 0xBF, 0x79, 0x2D, 0x59, 0x14, 0x6F, 0xA3, 0x22, 0x86, 0x97, 0x6F, 0xF5, 0x91, 0x72, 0x62, 0x96, 0x38, 0xE1, 0xA0, 0x70, 0xCB, 0x0F, 0x0E, 0xCB, 0xF8, 0x09, 0xF9, 0xF5, 0xB8, 0x73, 0xFB, + 0xEF, 0x96, 0x87, 0x4F, 0xCD, 0xED, 0x58, 0xA2, 0xC0, 0xA4, 0x99, 0x06, 0xD9, 0x09, 0x1D, 0x29, 0xB2, 0x1D, 0x0A, 0x7B, 0x89, 0x94, 0x52, 0x5D, 0x08, 0x88, 0x74, 0x8F, 0xB7, 0xDE, 0xE1, 0x60, + 0xF2, 0xFC, 0xC7, 0x89, 0x52, 0xBB, 0x57, 0xBE, 0x4D, 0x36, 0x68, 0x5B, 0xE4, 0xF2, 0xB1, 0x45, 0xBC, 0xAC, 0x40, 0xE0, 0xDB, 0x30, 0x60, 0x87, 0x2D, 0x81, 0x76, 0x63, 0x91, 0xD4, 0xEC, 0x0B, + 0x04, 0x60, 0x9F, 0x4F, 0x2D, 0xA2, 0x28, 0x94, 0x15, 0x45, 0x8D, 0x5F, 0x15, 0x22, 0x3C, 0x8E, 0x91, 0x11, 0x88, 0xC7, 0x82, 0x5F, 0x52, 0xA0, 0xA3, 0xA2, 0xC2, 0xCA, 0x8B, 0x62, 0xA7, 0x4B, + 0x03, 0x71, 0x59, 0xE5, 0x4D, 0x99, 0x73, 0xC8, 0x00, 0x54, 0x3D, 0x2F, 0x6C, 0x4C, 0x0D, 0x9E, 0x3B, 0x09, 0x39, 0xC1, 0xC1, 0x68, 0x05, 0xE5, 0x79, 0x46, 0x95, 0x49, 0x9C, 0xE0, 0x13, 0xCF, + 0xB9, 0xB0, 0xEA, 0xEE, 0xD8, 0xDD, + }, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 4668, + .sig = { + 0x37, 0xBD, 0x0C, 0xCB, 0xC5, 0x4E, 0x5A, 0x48, 0x0F, 0x2F, 0xBB, 0x8E, 0xF3, 0x87, 0x9E, 0x83, 0x40, 0xD7, 0xF6, 0xC7, 0x42, 0x42, 0xAD, 0x44, 0xD3, 0xE8, 0xB0, 0x78, 0x3C, 0xC5, 0xBF, 0x21, + 0x36, 0xD7, 0xBD, 0x4A, 0x32, 0xA9, 0x55, 0x2F, 0xE0, 0xE8, 0xAF, 0x8E, 0x87, 0xD5, 0x41, 0x1D, 0x76, 0x8A, 0x69, 0x2F, 0xE2, 0xC5, 0x03, 0xA7, 0x0C, 0xCB, 0xC0, 0x3A, 0x34, 0xB3, 0xC1, 0xF0, + 0x81, 0x5B, 0x26, 0x4B, 0x57, 0x2A, 0x9E, 0x74, 0x60, 0x9B, 0x9A, 0xD7, 0x29, 0x3B, 0xE3, 0x72, 0x7B, 0xFE, 0x17, 0x58, 0x3B, 0x3B, 0x63, 0x4F, 0x0A, 0x11, 0x9D, 0x79, 0x3E, 0xB1, 0x4D, 0xFF, + 0x18, 0x64, 0x3D, 0x1C, 0x34, 0x6B, 0x65, 0xE5, 0x73, 0xEF, 0xB9, 0xD5, 0x3B, 0xFA, 0x4C, 0x20, 0x05, 0x5D, 0x55, 0xF7, 0x54, 0xAF, 0x2F, 0x73, 0xFC, 0x38, 0x62, 0x67, 0xD5, 0x89, 0x0B, 0x39, + 0x13, 0x01, 0x41, 0x55, 0x93, 0xB2, 0xC5, 0x69, 0x5B, 0x9C, 0x06, 0xF0, 0x01, 0xF8, 0x84, 0x5C, 0x7C, 0xFA, 0xD7, 0x7C, 0x04, 0xE4, 0x11, 0x65, 0x18, 0xDF, 0x80, 0xF0, 0x41, 0xA5, 0x8A, 0x85, + 0x74, 0x48, 0xE7, 0x68, 0xA7, 0x1A, 0x7A, 0x01, 0xF2, 0x43, 0x31, 0x70, 0xB3, 0x71, 0xE8, 0xE3, 0x01, 0xA5, 0x37, 0x87, 0xD5, 0xEC, 0x77, 0x05, 0xA5, 0xEE, 0x1F, 0xE4, 0xFC, 0x04, 0x91, 0xCD, + 0xC6, 0xC8, 0x76, 0x96, 0x8A, 0x60, 0x6E, 0xC1, 0x38, 0x6F, 0x45, 0x1C, 0xE8, 0x54, 0x77, 0x34, 0x8D, 0xE1, 0xC6, 0x8E, 0xCC, 0x33, 0x95, 0x41, 0x61, 0x24, 0x90, 0xB2, 0x4C, 0x24, 0x2D, 0x25, + 0x87, 0x39, 0x81, 0xF9, 0xDE, 0xA6, 0x6D, 0x13, 0xF3, 0xC2, 0x10, 0x93, 0xEA, 0x48, 0x11, 0x51, 0xD1, 0x76, 0xA5, 0x50, 0x08, 0x42, 0x55, 0x0C, 0x26, 0xD0, 0xAF, 0xB1, 0xC6, 0xAE, 0xBE, 0x8E, + 0x42, 0x67, 0xE3, 0x6F, 0xD5, 0x70, 0x1E, 0x45, 0xD1, 0xDF, 0x15, 0x95, 0x9C, 0x7D, 0xC4, 0x4E, 0x7F, 0x5B, 0x6B, 0xA8, 0xCA, 0x04, 0xED, 0xF1, 0xE3, 0xE6, 0x48, 0x69, 0xFA, 0x15, 0x3B, 0xA7, + 0x46, 0x7F, 0x0D, 0x7B, 0x2F, 0xDC, 0x91, 0x24, 0x3A, 0x22, 0x39, 0x06, 0xF1, 0xAE, 0xA0, 0xD9, 0xFC, 0x14, 0x0F, 0x70, 0xCD, 0x02, 0x5A, 0x31, 0xB4, 0x0F, 0x22, 0xC4, 0x71, 0xBD, 0xD2, 0x36, + 0x5E, 0xD6, 0x30, 0x2D, 0x14, 0x81, 0x31, 0x6E, 0xE3, 0xC4, 0xC1, 0x70, 0xA1, 0x62, 0xEF, 0xE9, 0xFF, 0x41, 0x85, 0xE4, 0x50, 0x08, 0xF0, 0x7F, 0x6B, 0xDB, 0xAC, 0x22, 0x1D, 0xEC, 0x0B, 0xF0, + 0xAF, 0x88, 0x4B, 0x16, 0xC9, 0x5F, 0x34, 0x35, 0x01, 0xAA, 0x09, 0x8A, 0xD4, 0xA1, 0xF8, 0x20, 0x68, 0xFA, 0x1F, 0xBF, 0xF0, 0xE0, 0x40, 0x94, 0x6D, 0xCD, 0x50, 0xBF, 0x00, 0x9D, 0xF1, 0xFC, + 0xA4, 0xA3, 0xAA, 0xDB, 0x1C, 0x29, 0x51, 0xC0, 0x86, 0xD2, 0x7F, 0x20, 0x02, 0xDF, 0xD8, 0x54, 0xE5, 0x98, 0x52, 0xF4, 0x15, 0x30, 0x90, 0xDD, 0xC1, 0xA2, 0x1A, 0x6E, 0x0B, 0xE5, 0x92, 0x18, + 0x7A, 0x68, 0xAE, 0x08, 0x5B, 0x1D, 0x5D, 0x98, 0xBE, 0x8F, 0xCE, 0x5E, 0x24, 0x03, 0x1F, 0x47, 0xF8, 0x34, 0x30, 0x6B, 0xE5, 0xA5, 0xB6, 0x80, 0xAC, 0xFC, 0xD9, 0xF4, 0x04, 0xC1, 0xDE, 0x85, + 0x79, 0x66, 0xD2, 0x54, 0x6E, 0x66, 0x94, 0x01, 0x5F, 0x05, 0x02, 0xD0, 0xE6, 0x56, 0x8C, 0x9A, 0xA1, 0xB1, 0x3B, 0x3D, 0x7B, 0x61, 0xEE, 0x6A, 0x3D, 0xA0, 0x16, 0xDD, 0x34, 0xD6, 0x44, 0xB1, + 0x29, 0x7E, 0x63, 0x8D, 0xF0, 0xFC, 0xB6, 0xF6, 0x85, 0x57, 0x7E, 0x16, 0x4F, 0x5D, 0x6A, 0xA6, 0xF0, 0x70, 0xC1, 0xD0, 0x21, 0x55, 0x8C, 0xBC, 0xFD, 0x6F, 0x9B, 0xA3, 0x75, 0xE2, 0x89, 0x1F, + 0x67, 0x26, 0xCC, 0xE4, 0xCE, 0xBC, 0x89, 0xA9, 0x63, 0x57, 0x93, 0x0D, 0x04, 0x4C, 0x16, 0xAB, 0x29, 0x45, 0x30, 0x2C, 0xE0, 0xF2, 0xB6, 0x46, 0x17, 0x04, 0x6C, 0x3C, 0x1C, 0x4A, 0x6B, 0x34, + 0xD5, 0xAA, 0x07, 0x4E, 0x5F, 0xCB, 0x10, 0xBB, 0xA4, 0xC2, 0xA6, 0x08, 0x26, 0x5F, 0x45, 0xD7, 0x45, 0x10, 0x75, 0x0E, 0xAC, 0x67, 0x3A, 0x82, 0x8D, 0x5D, 0x30, 0x8F, 0x34, 0x07, 0x92, 0x31, + 0x33, 0xD5, 0x50, 0xB2, 0x57, 0x85, 0xA8, 0x39, 0x02, 0x42, 0xDC, 0x27, 0xB0, 0x82, 0xD3, 0x87, 0xAB, 0xCC, 0xDA, 0x7C, 0xD4, 0xD6, 0xEE, 0x5E, 0xAB, 0x8D, 0x51, 0xC8, 0x76, 0x9C, 0x24, 0x3A, + 0x95, 0x88, 0xF0, 0x45, 0xCC, 0xD9, 0xA5, 0x17, 0x2D, 0x99, 0xD0, 0x4E, 0xE4, 0x39, 0x59, 0xDC, 0x4D, 0x95, 0xBE, 0xAC, 0x06, 0x14, 0xA2, 0xF8, 0x50, 0x97, 0xED, 0x1C, 0x47, 0x61, 0x38, 0x42, + 0x9D, 0x12, 0xC7, 0x75, 0x8F, 0xA5, 0x28, 0x75, 0xC7, 0x38, 0xD4, 0x6E, 0xF2, 0xD9, 0x67, 0x51, 0x90, 0xFB, 0x72, 0x65, 0xF9, 0xAA, 0xC8, 0xC6, 0xF1, 0x73, 0xE8, 0xD5, 0x5C, 0x6B, 0x33, 0x81, + 0x9F, 0xBF, 0x9B, 0x5B, 0xD3, 0x12, 0x4D, 0x30, 0xC5, 0x81, 0x3E, 0x44, 0x7F, 0xAE, 0x23, 0xFC, 0xA5, 0xDB, 0x43, 0x8E, 0xC5, 0xCC, 0x8A, 0x66, 0xDE, 0xEB, 0xEB, 0x39, 0x53, 0x49, 0x29, 0xCE, + 0x4C, 0xE0, 0xB9, 0x8F, 0x1C, 0xA0, 0xE2, 0xC7, 0xD4, 0x53, 0x81, 0xC8, 0xF2, 0xE2, 0xFD, 0x2F, 0xED, 0x40, 0x6B, 0x29, 0xCC, 0x6A, 0x09, 0xD8, 0x1B, 0x44, 0xA4, 0x4F, 0x16, 0xC1, 0x50, 0xD8, + 0x65, 0xE8, 0xEA, 0x60, 0x60, 0xA8, 0x58, 0x39, 0x7C, 0x07, 0xF8, 0x57, 0x3A, 0x9C, 0xA2, 0x93, 0x00, 0x7D, 0x1B, 0xE4, 0xDD, 0xD8, 0xA5, 0x37, 0xDD, 0x9A, 0x57, 0x7F, 0x5E, 0x42, 0xF3, 0xEC, + 0xB4, 0x8F, 0x75, 0x81, 0x51, 0xA4, 0x01, 0xCA, 0xF2, 0x26, 0xA4, 0x8D, 0x94, 0x81, 0x9D, 0x2A, 0x43, 0xED, 0x08, 0xCD, 0xB6, 0xAE, 0xDD, 0x64, 0x01, 0x14, 0x03, 0x22, 0x31, 0x3B, 0xFD, 0xE2, + 0x76, 0x05, 0x71, 0x7E, 0x35, 0x66, 0xDD, 0x31, 0xBB, 0x5C, 0x52, 0x71, 0x45, 0x90, 0x45, 0x93, 0xA4, 0x74, 0x41, 0xD2, 0xF3, 0xC7, 0x44, 0x2C, 0x63, 0x69, 0x5D, 0xD0, 0xC3, 0x60, 0xBD, 0xA9, + 0x95, 0xFB, 0xFE, 0xC3, 0xE6, 0xC6, 0x63, 0xD1, 0xD2, 0x2D, 0x89, 0x0D, 0x7D, 0xF7, 0x05, 0x98, 0xF1, 0xBB, 0xC6, 0x19, 0x2A, 0x4F, 0x3A, 0x0A, 0x45, 0x8A, 0x95, 0x44, 0xCA, 0xDD, 0x6F, 0x18, + 0xDF, 0xA9, 0xEE, 0xA6, 0xE3, 0x20, 0x6B, 0xDE, 0x60, 0xED, 0x1C, 0x57, 0xCC, 0xC8, 0x00, 0x5F, 0x7C, 0x7C, 0x82, 0x74, 0xC1, 0x40, 0x7C, 0x8F, 0xAF, 0x4E, 0xBD, 0x69, 0xD5, 0x76, 0x19, 0x79, + 0xF9, 0x07, 0xCF, 0xD0, 0x62, 0x4E, 0xC7, 0xBA, 0x1F, 0xD7, 0xB5, 0x67, 0x81, 0xAC, 0x71, 0xA4, 0xA5, 0x26, 0x84, 0xFF, 0xC3, 0x2D, 0x5B, 0x53, 0x3C, 0xB5, 0x6C, 0x07, 0xF6, 0x35, 0xF5, 0x79, + 0x69, 0xC8, 0xF1, 0x58, 0x8D, 0x34, 0xD0, 0xE7, 0xA1, 0xC7, 0xA9, 0x42, 0xAA, 0xA3, 0xF3, 0x56, 0x0B, 0x0D, 0xB4, 0xF8, 0xCE, 0xBC, 0xAF, 0x6F, 0x25, 0x24, 0x11, 0x4A, 0x5F, 0x6A, 0xF7, 0x1B, + 0x5F, 0x50, 0xE9, 0x42, 0xE6, 0x74, 0xA8, 0x77, 0xC1, 0x74, 0xD9, 0x22, 0x00, 0x86, 0x5A, 0x5A, 0x06, 0xFB, 0x2D, 0x7F, 0xB4, 0x74, 0x41, 0x46, 0x75, 0xED, 0x31, 0x72, 0xF5, 0xF1, 0x53, 0x8F, + 0x58, 0x1E, 0xDE, 0x5E, 0xDD, 0x74, 0x5B, 0x55, 0xF9, 0xA2, 0xFC, 0x49, 0x95, 0xEB, 0x98, 0x4B, 0x8A, 0x12, 0xD6, 0xF6, 0x5A, 0xAE, 0xDF, 0x8D, 0x8D, 0x6F, 0xF5, 0x3C, 0xE2, 0x38, 0xC3, 0xA6, + 0x6C, 0xF2, 0x34, 0xF5, 0x94, 0x36, 0x47, 0x1C, 0x9F, 0xCB, 0xD3, 0x8E, 0x7F, 0x26, 0xBD, 0xF9, 0x74, 0x1B, 0x59, 0x9E, 0x16, 0xB8, 0xF7, 0xED, 0x46, 0x44, 0xBB, 0x6A, 0xBE, 0x81, 0xBB, 0x94, + 0x0C, 0x24, 0xFA, 0x62, 0x0F, 0x44, 0x35, 0x84, 0xF9, 0x9B, 0xB9, 0xDC, 0x25, 0x71, 0xB5, 0xEB, 0x81, 0x19, 0x27, 0x52, 0x9C, 0x7A, 0xDC, 0xEB, 0xEE, 0xF7, 0xAF, 0x05, 0xBA, 0x7E, 0x88, 0x89, + 0x9F, 0xAB, 0xF8, 0x74, 0x0F, 0xCD, 0xD1, 0x27, 0x5B, 0x12, 0xF7, 0x2A, 0x75, 0xC6, 0xD0, 0x00, 0x56, 0x5C, 0x5A, 0xC8, 0x8F, 0xB1, 0xFD, 0x99, 0x5B, 0x84, 0xED, 0x38, 0x4D, 0x5D, 0x6A, 0x60, + 0x29, 0x37, 0x37, 0xD7, 0x2C, 0xC1, 0x09, 0x44, 0x36, 0x39, 0x71, 0xDA, 0x44, 0xD5, 0xEA, 0xE9, 0xE8, 0xB1, 0xE8, 0x0D, 0x75, 0x76, 0xC5, 0x0A, 0xAF, 0xF6, 0x7E, 0x42, 0x31, 0x96, 0xF3, 0x78, + 0x57, 0xD1, 0xD2, 0x35, 0xAB, 0x28, 0x39, 0xAE, 0x37, 0x79, 0xF9, 0xF2, 0xF9, 0xB7, 0x59, 0xFC, 0x52, 0xDA, 0xAE, 0xB8, 0x63, 0x7B, 0x8F, 0x4F, 0xC9, 0x0B, 0xD9, 0x4A, 0xDB, 0x6F, 0x57, 0x72, + 0x20, 0x82, 0xE9, 0x43, 0xD7, 0xCE, 0x3E, 0x73, 0x50, 0x1D, 0x8C, 0x93, 0xB5, 0x21, 0x2D, 0xEC, 0xE4, 0x95, 0x35, 0x53, 0x6E, 0xFC, 0xEA, 0xB8, 0xB8, 0x5E, 0xB2, 0xAA, 0x94, 0xCB, 0xE7, 0x7B, + 0xAA, 0xDF, 0x46, 0x58, 0x92, 0x01, 0xA3, 0xA8, 0xAC, 0xA4, 0x83, 0x9E, 0x51, 0x9B, 0x6F, 0xD0, 0xCC, 0x52, 0xEA, 0x58, 0xA8, 0xAC, 0x08, 0xDC, 0x15, 0xEE, 0xF4, 0x8E, 0xDB, 0x89, 0xA1, 0xFC, + 0x46, 0xE7, 0x13, 0x53, 0xFE, 0x73, 0xF6, 0x8E, 0x0F, 0x48, 0x55, 0xB7, 0xFF, 0x73, 0x27, 0xAE, 0x4B, 0xCB, 0xA0, 0x9D, 0xE0, 0x33, 0x53, 0xD4, 0x1E, 0xDE, 0x26, 0x78, 0x5A, 0x94, 0x49, 0x6A, + 0xCB, 0x4E, 0x74, 0x3B, 0xA0, 0x65, 0xD1, 0x79, 0x3F, 0xBE, 0x5B, 0x29, 0x3A, 0x77, 0x1C, 0xCB, 0x8B, 0x8D, 0x8B, 0xD2, 0x76, 0x77, 0xD5, 0xFF, 0xF7, 0x43, 0xF9, 0x49, 0x77, 0x21, 0x9D, 0x55, + 0x57, 0x35, 0xE5, 0xD0, 0xAC, 0xE1, 0x18, 0xC2, 0x57, 0x1F, 0xC6, 0x96, 0xAF, 0x1F, 0xB0, 0xA1, 0x97, 0x6A, 0x37, 0x85, 0xB0, 0x89, 0x61, 0x11, 0x7F, 0x19, 0x98, 0xB7, 0xE6, 0x1C, 0xF8, 0x14, + 0xFE, 0x91, 0xA8, 0xB8, 0x1D, 0x62, 0xE4, 0x8D, 0x93, 0xB0, 0x28, 0x0D, 0xBA, 0xBF, 0x18, 0xE1, 0x12, 0x12, 0x43, 0xBF, 0xF3, 0x7B, 0x5A, 0xF7, 0x1E, 0x29, 0xA3, 0x1B, 0x48, 0x4A, 0xDA, 0x4F, + 0x1F, 0xBC, 0x88, 0x30, 0x11, 0x27, 0x76, 0x60, 0xAE, 0xB4, 0x71, 0xB3, 0x09, 0xFA, 0x00, 0x32, 0x23, 0x5B, 0x3B, 0x2E, 0x2B, 0x2C, 0xAF, 0xCC, 0xC5, 0x44, 0x61, 0xB0, 0xB4, 0x5A, 0xE1, 0x5D, + 0x92, 0xAD, 0x61, 0xB6, 0x4C, 0x5F, 0x37, 0x4A, 0x23, 0x74, 0x44, 0xF9, 0x63, 0x1D, 0xE4, 0x3C, 0x0B, 0x67, 0x8D, 0x03, 0xB6, 0x4E, 0xA3, 0xF9, 0x9B, 0xBB, 0xD1, 0x79, 0x61, 0x15, 0x39, 0xFC, + 0x91, 0x69, 0x3B, 0x81, 0xE6, 0xA2, 0xF2, 0xFC, 0x81, 0x70, 0xE8, 0xBF, 0xD6, 0xD5, 0xB7, 0x8A, 0x5C, 0xD6, 0x44, 0x88, 0x1A, 0x67, 0xFD, 0x28, 0xAC, 0xDA, 0x74, 0x70, 0x58, 0x47, 0x27, 0x6C, + 0x16, 0xBD, 0xF0, 0x9E, 0xBE, 0xBB, 0x21, 0x8C, 0xC6, 0x89, 0xB4, 0x50, 0x85, 0x43, 0xC3, 0x9E, 0xA6, 0x56, 0x44, 0xA7, 0xF3, 0x3D, 0xF4, 0x7D, 0x32, 0x72, 0xA3, 0x7C, 0xA8, 0x30, 0x76, 0x7B, + 0x23, 0xF5, 0x52, 0xA1, 0xB3, 0x89, 0xF1, 0x4B, 0xE8, 0x71, 0xFF, 0x72, 0x59, 0xFB, 0x3A, 0x32, 0x93, 0x0F, 0x56, 0xDD, 0x42, 0x71, 0xF0, 0x21, 0xAA, 0xAC, 0xD7, 0xA2, 0xAC, 0x82, 0x03, 0xCF, + 0x69, 0xE9, 0x64, 0x30, 0xA1, 0x6A, 0x2F, 0x96, 0xC1, 0x1F, 0xD2, 0xCD, 0x44, 0xE0, 0x86, 0xE1, 0x16, 0x8A, 0x8C, 0x1A, 0x63, 0x7E, 0x23, 0x21, 0xF6, 0x0C, 0xA5, 0x93, 0x0C, 0x02, 0xF9, 0x2D, + 0xFF, 0x2D, 0x30, 0xAB, 0x10, 0x5A, 0xF8, 0x46, 0xB1, 0x6A, 0x90, 0xE2, 0xA7, 0x4D, 0xBC, 0x97, 0xDA, 0x40, 0xA1, 0x3F, 0x40, 0x5B, 0x71, 0x04, 0xBF, 0x2F, 0x22, 0xFC, 0xA4, 0x2E, 0x3A, 0x50, + 0x0A, 0x72, 0x7A, 0xE1, 0xEA, 0x24, 0x01, 0x21, 0x60, 0x16, 0xFE, 0x8B, 0xF0, 0xDD, 0xBA, 0xE6, 0x8E, 0xD8, 0x74, 0x17, 0xFA, 0x76, 0x0D, 0xBA, 0x07, 0xD8, 0x4C, 0x26, 0x9C, 0xF4, 0x2B, 0xBE, + 0xB3, 0x7D, 0x5B, 0x90, 0xEB, 0x23, 0x69, 0x76, 0xB8, 0x6F, 0x4D, 0x8F, 0x35, 0xE7, 0x82, 0x83, 0x7E, 0x32, 0xA1, 0x95, 0xF9, 0xCF, 0xD6, 0xC6, 0x73, 0x53, 0x6A, 0xA0, 0x43, 0x5B, 0x38, 0x0C, + 0x02, 0xD1, 0xB7, 0xB0, 0xDE, 0x3C, 0x47, 0x9F, 0xE6, 0xB5, 0xFE, 0x6C, 0xF9, 0x7C, 0x3B, 0xD7, 0x46, 0x10, 0xCF, 0x15, 0x06, 0xE5, 0x99, 0x86, 0xF3, 0x81, 0x46, 0xB9, 0xA8, 0x96, 0x3C, 0xAE, + 0x08, 0x00, 0x30, 0x75, 0xFF, 0x60, 0x7D, 0x47, 0x0E, 0x87, 0xA7, 0x2E, 0x8F, 0xFB, 0xC7, 0xE1, 0x38, 0x38, 0xDA, 0x93, 0xDC, 0x3A, 0x4B, 0x3E, 0x52, 0x34, 0x75, 0xCD, 0xC4, 0xE4, 0x8C, 0x2A, + 0x54, 0x5F, 0x30, 0xE5, 0x89, 0x24, 0x7C, 0x64, 0x62, 0x2F, 0xA1, 0x05, 0x59, 0xB7, 0x24, 0xBB, 0x5F, 0xE8, 0x73, 0xED, 0xDF, 0x78, 0x38, 0xE1, 0x83, 0x2A, 0xD2, 0x17, 0xD4, 0xE8, 0x0B, 0x58, + 0xB9, 0xFB, 0x39, 0xB6, 0x6C, 0xBE, 0x9F, 0x26, 0x48, 0x09, 0xEE, 0xD5, 0x94, 0x23, 0xF0, 0xA3, 0xCD, 0x3F, 0x00, 0xAD, 0xFC, 0x47, 0x42, 0xCE, 0x1B, 0x3C, 0xB6, 0x5B, 0x2B, 0xD2, 0xE3, 0x10, + 0x59, 0x50, 0x9A, 0xFC, 0x7E, 0x48, 0x36, 0xDF, 0x0A, 0xE6, 0xF9, 0xD5, 0xC0, 0x63, 0x30, 0x95, 0x3F, 0xA2, 0xBB, 0x6F, 0xD0, 0x18, 0x7A, 0x6C, 0xAB, 0x88, 0x14, 0xEE, 0x12, 0xD1, 0x4E, 0xBC, + 0x6D, 0xEF, 0xFC, 0x23, 0xE1, 0xC9, 0x01, 0x65, 0xE2, 0xE7, 0x78, 0x59, 0x45, 0xF1, 0x8B, 0xCC, 0x74, 0xD8, 0xB1, 0xC6, 0xAF, 0xA1, 0x5B, 0x32, 0x6C, 0x04, 0x7D, 0x94, 0x66, 0x8C, 0x03, 0x32, + 0xD1, 0x47, 0xAF, 0x57, 0x52, 0x17, 0x64, 0x52, 0xC7, 0x12, 0x20, 0xB0, 0xA4, 0x32, 0xD4, 0x89, 0x9B, 0x6C, 0xEA, 0xA5, 0x87, 0x59, 0x9C, 0xAC, 0xF0, 0x04, 0xBA, 0x12, 0xA9, 0x0B, 0x26, 0x06, + 0x21, 0x43, 0x06, 0xFA, 0x30, 0x0A, 0x4A, 0x13, 0xBF, 0x8F, 0x99, 0x4F, 0x46, 0xF5, 0xDF, 0x92, 0xE6, 0xD3, 0xBF, 0x47, 0x2C, 0xF7, 0x29, 0xFF, 0xF6, 0x66, 0xF2, 0x07, 0xEA, 0x71, 0xD5, 0x2C, + 0xF6, 0xF2, 0xB1, 0x9C, 0x87, 0xCE, 0xAF, 0x08, 0xCD, 0x44, 0x5D, 0x18, 0x4F, 0x89, 0x81, 0xCA, 0x28, 0xCB, 0xFE, 0xA0, 0x03, 0x06, 0xAC, 0x76, 0x8B, 0x47, 0x15, 0x42, 0xF3, 0x27, 0x48, 0x76, + 0x68, 0x4B, 0xCE, 0x7C, 0x17, 0xEB, 0xEC, 0x6C, 0xC6, 0xD7, 0xF9, 0x0E, 0xC1, 0x3D, 0xA9, 0x4C, 0xD7, 0xB4, 0xE9, 0x8E, 0x1C, 0xFA, 0xBA, 0x8F, 0x9C, 0xDD, 0xBF, 0x08, 0xCF, 0xD7, 0xDD, 0x5E, + 0x3A, 0x73, 0x25, 0x66, 0x36, 0x65, 0x98, 0x0D, 0x3F, 0x55, 0x59, 0x22, 0x60, 0x8A, 0x05, 0xD9, 0xDC, 0x20, 0x76, 0x69, 0x29, 0x41, 0x30, 0x66, 0xB3, 0xB1, 0xAF, 0x98, 0x44, 0x31, 0x34, 0x5F, + 0xD0, 0x12, 0x1D, 0x16, 0x42, 0xEA, 0xB5, 0x84, 0xF7, 0x47, 0x37, 0x3D, 0x08, 0xCE, 0x5B, 0x2E, 0x26, 0xE7, 0x6B, 0x51, 0xAB, 0x58, 0xE3, 0x9E, 0x6F, 0x9E, 0x6C, 0x4C, 0x33, 0xF1, 0x52, 0xE5, + 0x03, 0x7F, 0x7F, 0x52, 0x76, 0x0A, 0x98, 0x36, 0x94, 0x1D, 0x43, 0xF4, 0x3C, 0x2E, 0x8C, 0x34, 0x6E, 0x40, 0x4A, 0xF3, 0x51, 0x80, 0x13, 0x3C, 0x2C, 0x8B, 0x44, 0x03, 0x86, 0x98, 0xFB, 0xE6, + 0xE8, 0x44, 0xEB, 0xC9, 0x66, 0x57, 0xD5, 0xD3, 0x24, 0xCE, 0xB2, 0xCC, 0x38, 0xA4, 0xF2, 0xE3, 0xB0, 0x09, 0x38, 0x39, 0x3B, 0x05, 0x4E, 0x19, 0xA1, 0xAF, 0x2C, 0x7E, 0x2C, 0xBB, 0xC1, 0xC4, + 0x52, 0xB6, 0x9D, 0x02, 0xA4, 0xBF, 0x04, 0xEB, 0x58, 0x42, 0xAA, 0x6A, 0x0A, 0xF8, 0xFB, 0x9D, 0x85, 0xD7, 0x98, 0x5B, 0x9B, 0xB2, 0x3D, 0x86, 0x06, 0x24, 0xB4, 0xE4, 0x04, 0x7E, 0x14, 0x26, + 0xF7, 0x17, 0x76, 0x7E, 0x51, 0x5C, 0x3D, 0x99, 0xF4, 0xF3, 0xA1, 0x05, 0x66, 0x56, 0x23, 0x2A, 0x21, 0x1C, 0xC2, 0xC8, 0x07, 0xF1, 0xF9, 0xF9, 0x61, 0x1D, 0xC8, 0xAE, 0x50, 0x81, 0x94, 0xF7, + 0xD6, 0x18, 0x2E, 0xE3, 0xAE, 0x96, 0x71, 0xB3, 0x45, 0xD0, 0x23, 0x18, 0x94, 0x78, 0x6E, 0x70, 0x72, 0x42, 0xF0, 0x68, 0x80, 0x69, 0x5A, 0x3F, 0xA6, 0x26, 0x89, 0x15, 0x74, 0xFA, 0xEE, 0xEE, + 0x83, 0x39, 0xDE, 0xBE, 0x23, 0x0E, 0xE7, 0x6B, 0x82, 0xA9, 0xAE, 0x4F, 0x03, 0xD9, 0xCC, 0xA2, 0x8F, 0x3B, 0x9F, 0x2F, 0x06, 0xAC, 0x23, 0xE3, 0xD2, 0xCF, 0x76, 0xF0, 0x19, 0x50, 0x6F, 0xEC, + 0x5C, 0x6E, 0x99, 0x07, 0x58, 0x7F, 0xB3, 0xBF, 0x4C, 0x2B, 0xE6, 0x58, 0xC5, 0x6E, 0xD6, 0x31, 0x88, 0x46, 0x56, 0xD6, 0xC2, 0x0E, 0xE1, 0x0B, 0x78, 0xD8, 0xF2, 0xD8, 0x01, 0x82, 0x30, 0xCD, + 0xF9, 0x5E, 0xB8, 0x6E, 0x9C, 0xFD, 0xA2, 0xE1, 0x55, 0xBA, 0x33, 0x58, 0x12, 0xFC, 0x72, 0xEB, 0x88, 0x0B, 0xEA, 0x3A, 0x8C, 0x3A, 0x98, 0xCB, 0x56, 0x71, 0xE0, 0xE4, 0x03, 0x70, 0x4A, 0x55, + 0x33, 0x62, 0x5B, 0x3E, 0xFA, 0x5C, 0xD3, 0x6C, 0x93, 0xDA, 0x37, 0x77, 0x21, 0xBF, 0x43, 0x82, 0xA0, 0xD0, 0x11, 0x77, 0xBC, 0xC5, 0xBC, 0xB4, 0xB7, 0x08, 0x23, 0x32, 0xE3, 0xE5, 0x85, 0x1B, + 0x17, 0xF7, 0xB9, 0xD9, 0x10, 0xD2, 0x19, 0xEC, 0x5F, 0x98, 0xB9, 0xCE, 0x2E, 0xD2, 0x7F, 0x40, 0xB5, 0x72, 0x13, 0x8F, 0xE9, 0xA0, 0x3F, 0x15, 0x48, 0x65, 0x23, 0xB2, 0x9A, 0xA4, 0xC6, 0x07, + 0x60, 0x17, 0xEF, 0xD2, 0x70, 0x70, 0x56, 0x0A, 0xC6, 0x13, 0xB3, 0x1D, 0x76, 0xB9, 0x60, 0x07, 0xEA, 0x98, 0xD7, 0xB0, 0x1D, 0x9A, 0x92, 0x54, 0x0C, 0x6A, 0x03, 0x0C, 0x4D, 0x0B, 0x98, 0x50, + 0x8A, 0x14, 0x51, 0xE6, 0x48, 0x7F, 0x11, 0x2E, 0xF9, 0xE9, 0x05, 0xBA, 0x88, 0x92, 0x7A, 0xD6, 0x19, 0xEE, 0xEC, 0x6B, 0x58, 0xEE, 0xF0, 0x62, 0xE9, 0x1D, 0x35, 0x10, 0xB4, 0xED, 0xDA, 0xB2, + 0xE5, 0xF9, 0x15, 0x46, 0x70, 0xEA, 0x8C, 0xF0, 0x00, 0x4C, 0xA4, 0xE2, 0xCC, 0xB5, 0xCE, 0x6C, 0x18, 0x70, 0xDA, 0x6B, 0xD8, 0xFD, 0xDC, 0x36, 0x41, 0x03, 0x91, 0x08, 0x82, 0x23, 0xF1, 0x53, + 0xF6, 0x83, 0x97, 0x6B, 0xAB, 0x00, 0x87, 0xB2, 0xAF, 0x15, 0x7C, 0xA7, 0x89, 0x3E, 0x5C, 0x34, 0xF8, 0x38, 0xB2, 0x2A, 0xE6, 0x51, 0x4A, 0xB3, 0x81, 0xF4, 0x7A, 0x63, 0x3E, 0xC8, 0x9A, 0x2E, + 0x1E, 0x51, 0x11, 0x18, 0x75, 0xB3, 0xAE, 0x9A, 0xEB, 0x66, 0x7D, 0xC8, 0x38, 0x6D, 0xB8, 0x1F, 0x13, 0xFF, 0x8D, 0xF7, 0x38, 0xB1, 0x02, 0x15, 0xDA, 0x52, 0x21, 0x01, 0xEF, 0xB8, 0xAD, 0xC9, + 0xB1, 0x08, 0x75, 0xA4, 0x79, 0xB6, 0x47, 0x93, 0xB2, 0x4C, 0x67, 0x68, 0x41, 0xE3, 0x5C, 0x97, 0xA8, 0xE7, 0xEE, 0xBC, 0x6C, 0x51, 0x72, 0xCA, 0x88, 0x66, 0x1F, 0x2B, 0x62, 0x86, 0x46, 0x31, + 0x2A, 0x68, 0x8C, 0xCC, 0x12, 0x43, 0x7D, 0x70, 0x39, 0x0C, 0x3E, 0x16, 0x21, 0x92, 0x0E, 0x65, 0x53, 0x98, 0xFF, 0x9A, 0x7E, 0x53, 0x74, 0xDF, 0xEC, 0xE4, 0x00, 0x19, 0x5B, 0x6A, 0x43, 0x1C, + 0xDC, 0xC4, 0xB2, 0xF4, 0x4D, 0xAA, 0xC9, 0xBF, 0x91, 0x5E, 0x1B, 0x23, 0xA8, 0x5F, 0xED, 0x35, 0xE3, 0xC4, 0x3F, 0xCF, 0x02, 0x13, 0x04, 0x02, 0x10, 0x94, 0x83, 0x13, 0x48, 0x98, 0x37, 0x08, + 0x0F, 0x1D, 0x80, 0x30, 0x27, 0xB0, 0x98, 0x95, 0x11, 0xD0, 0x63, 0x16, 0x7B, 0x36, 0x58, 0xD3, 0xF9, 0x8C, 0x0D, 0x2C, 0xA8, 0x79, 0x76, 0x53, 0x49, 0x28, 0x98, 0xC8, 0x14, 0x0E, 0x21, 0x86, + 0x9C, 0x56, 0x3A, 0x5C, 0x03, 0xB7, 0x86, 0x07, 0x8F, 0x63, 0x4D, 0x75, 0xED, 0x2B, 0xDA, 0xD2, 0x74, 0x22, 0x51, 0xB6, 0x36, 0x48, 0x7D, 0x1A, 0xFF, 0xAB, 0xF3, 0x1E, 0x66, 0x46, 0x98, 0xC1, + 0x77, 0x3F, 0x4E, 0x4D, 0xE9, 0xF2, 0xC3, 0xA4, 0xFE, 0xE7, 0x58, 0xEA, 0x07, 0x34, 0x89, 0x46, 0x99, 0x48, 0xBC, 0x9B, 0x50, 0xDB, 0x60, 0xD0, 0x5D, 0x9F, 0x18, 0x31, 0x41, 0x48, 0x94, 0xC2, + 0x06, 0x19, 0x0E, 0xCD, 0xE8, 0xF2, 0x49, 0xBD, 0x43, 0x57, 0x7C, 0x8D, 0x40, 0xCA, 0x61, 0x1D, 0x23, 0xB6, 0xF7, 0x54, 0xCB, 0x06, 0xC6, 0x77, 0xC7, 0x1A, 0x77, 0x00, 0xCB, 0x8A, 0xF9, 0x30, + 0xC5, 0xFF, 0xDB, 0x55, 0x4C, 0xA6, 0xAB, 0xE6, 0xD0, 0x83, 0xEE, 0x1A, 0x5A, 0xBF, 0xAA, 0x27, 0xA6, 0xF3, 0x1A, 0x83, 0x02, 0xBF, 0xD5, 0x78, 0xBC, 0x52, 0x93, 0xBD, 0xA4, 0xC1, 0x84, 0xE7, + 0xD7, 0xBB, 0x58, 0x9F, 0x6D, 0xEA, 0x11, 0xC9, 0xF3, 0x9A, 0xB9, 0xCD, 0x09, 0x8A, 0x72, 0x81, 0x63, 0xD7, 0x96, 0x2B, 0x6A, 0x40, 0x06, 0xF2, 0x65, 0x27, 0x73, 0xD5, 0xD8, 0xCA, 0xDA, 0x35, + 0xFB, 0x07, 0xDD, 0x8D, 0x39, 0x2D, 0xF7, 0x07, 0x9D, 0x1D, 0x72, 0x1D, 0xFA, 0xEC, 0xFF, 0xAC, 0xDB, 0x80, 0x81, 0x42, 0xFB, 0xA4, 0xF3, 0xC9, 0xB5, 0xC3, 0x1C, 0x81, 0xBB, 0x58, 0xA9, 0xAA, + 0x30, 0x1F, 0x3D, 0x54, 0xEB, 0x4B, 0x0D, 0xBF, 0xF7, 0xF2, 0x67, 0x73, 0xB4, 0x56, 0xD5, 0xC0, 0x2F, 0x94, 0x25, 0x4E, 0xB7, 0x7E, 0x35, 0x3A, 0x68, 0x75, 0x3D, 0xCD, 0xC6, 0x2E, 0xC2, 0x3B, + 0xDD, 0x5D, 0x6B, 0xBA, 0x07, 0xDB, 0x3E, 0xAC, 0x51, 0xE6, 0x4C, 0x34, 0xB4, 0xB5, 0x34, 0x38, 0xBF, 0x7C, 0x6E, 0xF9, 0xC6, 0x23, 0x7B, 0x68, 0xF6, 0x98, 0xE4, 0x31, 0x50, 0x77, 0x23, 0xA2, + 0xE3, 0xBC, 0x43, 0xDD, 0xB6, 0xD9, 0x52, 0xA4, 0xF1, 0x2B, 0x43, 0xF7, 0x64, 0xF7, 0x5B, 0x5C, 0x6C, 0xB8, 0x82, 0xF7, 0xFE, 0xB7, 0x38, 0xAE, 0x3F, 0xB9, 0x1C, 0xBF, 0x49, 0x7E, 0x8E, 0x1D, + 0x1B, 0x1D, 0x59, 0x22, 0x79, 0xAF, 0x26, 0x16, 0x6C, 0xCA, 0x5A, 0xBD, 0xD2, 0x8E, 0x6E, 0xFF, 0x4F, 0xBA, 0x74, 0x60, 0x5E, 0xA8, 0x85, 0xCE, 0xEB, 0x5A, 0x01, 0xEA, 0xFD, 0xE3, 0x16, 0x93, + 0x9C, 0x35, 0xB8, 0x01, 0x0D, 0xD8, 0x57, 0x9A, 0x3A, 0x94, 0xFC, 0x68, 0x5E, 0xEB, 0x1F, 0x62, 0x83, 0xC5, 0xE6, 0xAD, 0x51, 0xE8, 0x2A, 0x93, 0x51, 0xC9, 0xD1, 0xA3, 0xFD, 0xB8, 0xB3, 0xD2, + 0x6D, 0x02, 0x93, 0xA8, 0xBC, 0xBF, 0x25, 0x6B, 0x5E, 0x5B, 0xB3, 0x31, 0x23, 0x3A, 0x30, 0xDA, 0xF0, 0xFE, 0x4A, 0xDE, 0x80, 0x82, 0xB3, 0x03, 0xC3, 0x9E, 0x55, 0x1D, 0xBC, 0xC3, 0x02, 0xBF, + 0x9B, 0x8A, 0xD3, 0x93, 0x3C, 0xB9, 0xAD, 0x90, 0x0A, 0x68, 0x25, 0x36, 0x7E, 0x15, 0x3E, 0x89, 0x6B, 0xC9, 0xAF, 0xDF, 0x8E, 0x40, 0x55, 0xA9, 0xD0, 0x9B, 0x85, 0x4C, 0xA8, 0x3D, 0x3A, 0xDF, + 0x6E, 0x00, 0x43, 0x75, 0xC4, 0xED, 0xE4, 0xEC, 0x5C, 0x57, 0x80, 0x5F, 0x79, 0xA2, 0x06, 0x03, 0x4C, 0x51, 0x40, 0xCC, 0x60, 0x27, 0x7E, 0xAA, 0x74, 0xCD, 0xEE, 0xE9, 0xF0, 0x49, 0x3E, 0x90, + 0x91, 0xC2, 0x29, 0x98, 0xB6, 0x13, 0x86, 0x3C, 0xE3, 0xAB, 0x77, 0x98, 0x39, 0x2E, 0x69, 0x67, 0x58, 0xC0, 0x32, 0x28, 0x6E, 0x10, 0x39, 0xBB, 0x13, 0x6C, 0x7C, 0x54, 0x30, 0xCB, 0xCD, 0x6D, + 0x99, 0x9A, 0xA1, 0xF7, 0xB2, 0x8B, 0xE6, 0x03, 0x32, 0xCE, 0x70, 0xF5, 0x6E, 0xE3, 0x1C, 0x9E, 0xAB, 0x2D, 0x1E, 0x41, 0x3F, 0x0E, 0x65, 0x59, 0xE1, 0xF5, 0xCC, 0x6A, 0x5A, 0xAA, 0x8A, 0xD2, + 0x64, 0x46, 0x88, 0x85, 0x52, 0x18, 0x1B, 0x8A, 0xA5, 0x30, 0xE4, 0xC6, 0x64, 0x68, 0x01, 0x08, 0x00, 0xAD, 0x5A, 0x94, 0xF3, 0xA0, 0xDD, 0x36, 0x9F, 0x1D, 0x5D, 0x16, 0xA8, 0x3A, 0x5F, 0xF7, + 0x49, 0xC5, 0xFE, 0xC8, 0x67, 0x2F, 0x92, 0xE5, 0xC8, 0x40, 0x0B, 0xD7, 0x67, 0x1F, 0x91, 0xFC, 0x06, 0x97, 0x21, 0x53, 0x14, 0xF0, 0x26, 0x51, 0x61, 0x42, 0xCA, 0xA6, 0x03, 0xED, 0x19, 0x11, + 0x5A, 0xAC, 0x9C, 0x32, 0x5D, 0x18, 0x34, 0x0E, 0x67, 0x62, 0xEF, 0xBA, 0xCF, 0xEF, 0x8E, 0x33, 0x13, 0x3C, 0x0F, 0x8F, 0x84, 0xBE, 0x6C, 0x1F, 0x95, 0xCB, 0x24, 0x45, 0x3D, 0xD8, 0x46, 0xEB, + 0xC6, 0x29, 0x5C, 0x7E, 0x7D, 0xF9, 0x44, 0xB0, 0x17, 0xF1, 0xEF, 0x8A, 0x47, 0x85, 0x22, 0x96, 0xF0, 0x91, 0x96, 0xD1, 0x51, 0xB7, 0x8D, 0x77, 0xC9, 0xC1, 0xDA, 0x7D, 0x99, 0x75, 0xE5, 0x89, + 0x83, 0xD3, 0x31, 0xE1, 0x78, 0x3F, 0xA6, 0x3B, 0xD9, 0x0C, 0x58, 0xC8, 0x2E, 0x4B, 0xFD, 0xDF, 0x8F, 0x0B, 0x4C, 0x37, 0xBB, 0xA4, 0x39, 0x07, 0x4F, 0x32, 0xE4, 0x1A, 0xBB, 0xCC, 0x90, 0xB5, + 0x6C, 0x6A, 0xD3, 0x6E, 0xC8, 0xAB, 0x1F, 0xB3, 0x34, 0xCE, 0x59, 0xDA, 0x0E, 0xEF, 0xBE, 0x46, 0x5B, 0xF9, 0x62, 0x67, 0x4D, 0x25, 0x81, 0x5F, 0x22, 0x10, 0x84, 0x86, 0x56, 0x93, 0xB0, 0x3A, + 0x44, 0xF6, 0x39, 0xF3, 0xA4, 0x7C, 0x36, 0xEE, 0xB2, 0x46, 0xD3, 0x90, 0x7D, 0x2F, 0x1D, 0x23, 0x78, 0xD7, 0xD7, 0x93, 0xD3, 0x95, 0xC3, 0x65, 0x52, 0x5A, 0x46, 0x5D, 0x9C, 0xE4, 0x15, 0x25, + 0x41, 0xE5, 0x94, 0xA7, 0x29, 0xAC, 0x62, 0xEE, 0x4E, 0x3A, 0xB5, 0x89, 0xE7, 0xB0, 0x01, 0xD5, 0xF2, 0x35, 0x4E, 0x3E, 0x30, 0xB1, 0x82, 0xBD, 0x69, 0xDC, 0x5A, 0x87, 0x7F, 0xF1, 0xCB, 0x87, + 0xFB, 0x9C, 0x25, 0x60, 0xBF, 0xE8, 0x2D, 0x3E, 0xDB, 0x06, 0x3B, 0xB7, 0x4D, 0x4B, 0x1F, 0x5C, 0xF3, 0x31, 0xB2, 0xD8, 0x4B, 0x45, 0x98, 0x8E, 0x04, 0xF7, 0x18, 0x32, 0xF0, 0x27, 0x2C, 0xD5, + 0xA8, 0x44, 0x91, 0x9E, 0xC3, 0x41, 0x3A, 0xE0, 0xE9, 0x9F, 0x0A, 0x8D, 0xAD, 0xC1, 0x87, 0xE9, 0xBD, 0x9A, 0x4D, 0xF9, 0xE1, 0x05, 0xD1, 0x81, 0x37, 0x60, 0xC4, 0xFA, 0x32, 0x95, 0xBC, 0x22, + 0x51, 0x7E, 0x89, 0x07, 0xD9, 0x85, 0xD2, 0x79, 0xEA, 0x25, 0x67, 0x4C, 0x78, 0x53, 0x18, 0x80, 0x5D, 0x1D, 0xBC, 0xD7, 0x97, 0x62, 0x46, 0x83, 0xC3, 0x63, 0xEA, 0xCA, 0xFE, 0x62, 0xC0, 0x78, + 0x83, 0x4A, 0x5B, 0x13, 0x78, 0x7F, 0xAF, 0x0A, 0xB3, 0xB4, 0xD2, 0x45, 0x71, 0x3B, 0x02, 0x22, 0x2A, 0x8A, 0x60, 0x56, 0x23, 0xA5, 0xE1, 0xE5, 0x0F, 0x5D, 0xBB, 0xAB, 0x95, 0x6A, 0xBC, 0xA5, + 0xF0, 0x64, 0x11, 0xD5, 0x97, 0xB0, 0xFB, 0x2D, 0x6D, 0xCC, 0x65, 0x0E, 0x77, 0x65, 0xF5, 0xE2, 0x3C, 0x4B, 0x8B, 0xC2, 0xB7, 0xAE, 0x0C, 0x88, 0x58, 0xB6, 0x50, 0xD1, 0x66, 0x89, 0x10, 0x38, + 0x54, 0x39, 0x2C, 0xB2, 0x41, 0x0E, 0xBD, 0x20, 0x8D, 0xF2, 0xE8, 0xD6, 0xF2, 0x21, 0x33, 0xCB, 0x63, 0xBC, 0x21, 0xE9, 0x69, 0xDC, 0x67, 0xA0, 0xE2, 0xEE, 0xDC, 0x42, 0x8E, 0x3B, 0x71, 0xC8, + 0x31, 0x89, 0x9B, 0x8D, 0x41, 0x22, 0xE5, 0x96, 0x69, 0xC1, 0x42, 0xBA, 0xB2, 0x0A, 0xFF, 0x7E, 0xD1, 0x89, 0x54, 0xB6, 0x52, 0x4B, 0x8C, 0x58, 0xD3, 0x91, 0xE3, 0x70, 0x61, 0xD1, 0xD5, 0x66, + 0xEA, 0x04, 0x42, 0x7E, 0x91, 0x44, 0x09, 0x5F, 0xDB, 0x1A, 0x28, 0xC1, 0xFD, 0x49, 0xCA, 0xD9, 0xFD, 0x55, 0xD7, 0x54, 0x7F, 0xF9, 0xD6, 0x0D, 0x54, 0xF7, 0x20, 0x5E, 0xBE, 0xD4, 0x96, 0xD1, + 0xE9, 0xDE, 0xDB, 0x8B, 0x28, 0xCE, 0xF8, 0x1D, 0x1A, 0xA5, 0x78, 0x05, 0x76, 0xD6, 0x7D, 0x70, 0x23, 0x21, 0xE5, 0x89, 0xD4, 0x4A, 0x60, 0xE2, 0x1F, 0xA0, 0x7B, 0xD9, 0x2D, 0xCF, 0xA1, 0x57, + 0xF1, 0x0D, 0xA6, 0x0F, 0xAD, 0x6E, 0x44, 0x28, 0x07, 0xD4, 0xE1, 0xCF, 0x5F, 0x7A, 0xBD, 0x0B, 0xB4, 0xBF, 0x1D, 0x7F, 0xF3, 0x6A, 0x0E, 0x63, 0x6E, 0x30, 0x0C, 0xD8, 0x57, 0x55, 0x33, 0x1B, + 0x22, 0x05, 0x97, 0x87, 0x23, 0xD9, 0xAC, 0xE6, 0xF2, 0xD5, 0x6F, 0xEC, 0x9D, 0x54, 0x59, 0x4C, 0xDB, 0x64, 0x3B, 0x8A, 0x9D, 0x8E, 0x6F, 0x76, 0x5C, 0xCE, 0xEF, 0x28, 0x19, 0xB3, 0xEF, 0x55, + 0xDE, 0x38, 0x9F, 0xDC, 0x00, 0x79, 0x27, 0xD2, 0x22, 0xF1, 0x1D, 0x22, 0x76, 0xDD, 0x18, 0xD4, 0xDF, 0x86, 0xE8, 0xE7, 0xE2, 0xA4, 0xD9, 0x94, 0x3D, 0xD8, 0x83, 0xD7, 0x0B, 0xC0, 0x45, 0xB6, + 0xAF, 0xAB, 0xED, 0xDF, 0x42, 0x18, 0xA2, 0x5A, 0xBF, 0x3F, 0xB0, 0xD4, 0x13, 0xD6, 0x18, 0x37, 0xC4, 0x5B, 0x86, 0xF9, 0xE6, 0xC6, 0x25, 0x53, 0x37, 0xC3, 0x8A, 0xF3, 0x5B, 0xE8, 0x2B, 0xE1, + 0xF0, 0x3A, 0xF0, 0x81, 0x1F, 0x2F, 0x1E, 0xEB, 0x25, 0x27, 0x6B, 0xF6, 0xAB, 0x27, 0xB9, 0x25, 0x64, 0x33, 0x4F, 0x06, 0x3A, 0x83, 0x18, 0xFC, 0x69, 0xC1, 0x34, 0x70, 0xDA, 0x6F, 0xD9, 0x47, + 0xB7, 0xEE, 0x2F, 0x67, 0xA7, 0x60, 0x5F, 0x6A, 0x57, 0x95, 0x3F, 0x96, 0xA3, 0x35, 0xB5, 0x50, 0x12, 0x63, 0x98, 0x67, 0x49, 0x02, 0x11, 0x88, 0x62, 0xF0, 0x86, 0x3F, 0x93, 0x13, 0xA3, 0x6A, + 0xD0, 0x57, 0x34, 0xE5, 0x1F, 0x54, 0x98, 0x62, 0x17, 0x0E, 0xC3, 0x69, 0x5A, 0x67, 0xE0, 0xC1, 0x6C, 0xDC, 0xDE, 0xA7, 0x7B, 0x39, 0x5D, 0x1F, 0xC4, 0xF8, 0xF1, 0x3A, 0x08, 0xBA, 0x8D, 0x4C, + 0xC4, 0x09, 0xCA, 0xBC, 0x9B, 0x15, 0xF1, 0x00, 0x7A, 0x4E, 0x3E, 0x4A, 0x71, 0x37, 0xB7, 0x00, 0xBE, 0xF5, 0xC3, 0x32, 0x97, 0x73, 0x5B, 0xE4, 0xC0, 0xAD, 0xB5, 0x4A, 0xA2, 0xDB, 0xE0, 0x96, + 0x2D, 0x16, 0x83, 0x55, 0x5C, 0xFC, 0xB8, 0x84, 0x17, 0xD7, 0x19, 0x4B, 0x7A, 0xDF, 0x09, 0xB3, 0xD2, 0xD5, 0xBA, 0xDE, 0xB1, 0xE8, 0x47, 0xAF, 0x62, 0x11, 0x65, 0x45, 0x4C, 0x4D, 0xA0, 0x0D, + 0x11, 0x85, 0x06, 0xE8, 0x25, 0xBD, 0x8F, 0x90, 0xDE, 0x0C, 0xC1, 0x1A, 0xFA, 0xD8, 0x5E, 0x08, 0xE9, 0x0E, 0xB5, 0xC4, 0x42, 0xD5, 0xB8, 0x5C, 0x9A, 0x9B, 0x86, 0xF2, 0x75, 0x8F, 0x4B, 0xB9, + 0xDA, 0x95, 0xA7, 0xB5, 0xB5, 0x85, 0xD6, 0x1A, 0x5C, 0x0E, 0x6E, 0x92, 0x0B, 0xBC, 0x43, 0x64, 0x97, 0xBB, 0x6C, 0x9A, 0xB8, 0x18, 0xAF, 0xCB, 0x5C, 0xE8, 0x14, 0x81, 0x09, 0xED, 0x99, 0x94, + 0x2E, 0x07, 0x90, 0xC5, 0xE2, 0x71, 0x4F, 0x4A, 0x88, 0x06, 0x74, 0xF4, 0xC6, 0x86, 0xF0, 0x7B, 0x48, 0xF5, 0xB8, 0x35, 0x9F, 0x9A, 0xF6, 0x3E, 0xB2, 0x05, 0xA3, 0x7B, 0xC0, 0xC6, 0x39, 0xDF, + 0x09, 0x3F, 0x88, 0xBB, 0x45, 0xCA, 0x1B, 0xA0, 0xDD, 0xD7, 0x1D, 0xB7, 0x4A, 0x22, 0xCE, 0x88, 0x4B, 0x39, 0x83, 0xD4, 0x54, 0xD5, 0x69, 0x56, 0x66, 0xED, 0x88, 0xDB, 0xB1, 0x66, 0xE9, 0x98, + 0x96, 0xEA, 0xBF, 0x67, 0x6B, 0xB8, 0x6D, 0x0E, 0xF3, 0xBD, 0xCF, 0x24, 0x1F, 0x50, 0xF2, 0x67, 0x2E, 0x3C, 0xD3, 0xBD, 0xAE, 0x60, 0xE6, 0xEC, 0xCD, 0xEF, 0x96, 0xDF, 0x63, 0x90, 0x88, 0xE4, + 0x45, 0x7A, 0xEE, 0xE7, 0x74, 0x6C, 0x24, 0xBD, 0x67, 0x6F, 0x3E, 0xFE, 0xA2, 0x7D, 0xDC, 0xDA, 0xC8, 0xA4, 0x1C, 0xA5, 0xBF, 0x9E, 0x03, 0xC8, 0xF5, 0xAF, 0xBB, 0xC8, 0x9B, 0x6D, 0x96, 0xBF, + 0x90, 0xD9, 0x4C, 0xFF, 0xD9, 0x1E, 0x3A, 0x8A, 0x07, 0xCC, 0xF0, 0x44, 0x93, 0xA5, 0xCB, 0x44, 0x1A, 0x9F, 0x59, 0x61, 0xEA, 0xC7, 0x1C, 0xEA, 0xB0, 0x4A, 0x78, 0xF7, 0x0B, 0x4F, 0x52, 0xF4, + 0x63, 0x09, 0x45, 0xAC, 0xC4, 0x5F, 0x4F, 0x83, 0xEE, 0x96, 0x7C, 0xF2, 0xB2, 0x37, 0x5D, 0x0F, 0xCE, 0x3A, 0x3F, 0x6E, 0x43, 0x96, 0x36, 0x14, 0xCC, 0xE0, 0x36, 0x03, 0xF0, 0x59, 0x7D, 0x30, + 0xE1, 0xD6, 0x75, 0xC0, 0x0F, 0x3C, 0xCA, 0xC4, 0x49, 0x21, 0xD2, 0x92, 0x28, 0xFF, 0x52, 0x96, 0xD4, 0x35, 0x25, 0x2F, 0x9C, 0xB3, 0x26, 0xA4, 0xD6, 0xFC, 0x34, 0xF0, 0x79, 0x89, 0xC1, 0x84, + 0x28, 0x86, 0x74, 0x59, 0xD1, 0x82, 0x95, 0xD2, 0xD6, 0x12, 0x10, 0x7F, 0x75, 0x35, 0xED, 0x27, 0xF6, 0x84, 0x6C, 0xA8, 0xD3, 0xB1, 0x73, 0x9D, 0x23, 0x45, 0xD2, 0x8B, 0xCC, 0xC4, 0xFD, 0x1A, + 0x63, 0x14, 0xFD, 0x47, 0x88, 0x9B, 0x53, 0xA1, 0xA7, 0x34, 0x63, 0x4B, 0xEC, 0x0C, 0x0A, 0x1C, 0x8A, 0x0A, 0x89, 0xAC, 0x66, 0xB0, 0xF4, 0xE5, 0x32, 0x8F, 0x76, 0x39, 0x2D, 0x01, 0x73, 0xE1, + 0x74, 0xEB, 0x8F, 0xA6, 0x0F, 0x86, 0xC9, 0x7F, 0x00, 0x20, 0xDC, 0xFA, 0x4E, 0x69, 0x94, 0xFC, 0x08, 0xFD, 0xCF, 0x40, 0x5A, 0x44, 0xB1, 0xC4, 0x8C, 0xC2, 0x1C, 0x51, 0xA0, 0x92, 0x81, 0x73, + 0x71, 0xF9, 0x6E, 0x64, 0xBD, 0x2B, 0x69, 0xBA, 0x79, 0xD7, 0xE4, 0xDD, 0x2C, 0x1F, 0x71, 0x8B, 0xF4, 0x56, 0x39, 0xCB, 0x45, 0x39, 0xE1, 0xF8, 0x9C, 0xF0, 0xE5, 0xEF, 0x25, 0x88, 0xE2, 0x5D, + 0xEB, 0x44, 0x10, 0x1D, 0x3C, 0x12, 0xE1, 0x4B, 0x99, 0x3C, 0x0A, 0xB3, 0x55, 0x61, 0x13, 0x82, 0x19, 0x59, 0xC6, 0xE9, 0xFC, 0x9A, 0xCC, 0x95, 0xBA, 0x17, 0x31, 0x4A, 0xC5, 0x6D, 0x2B, 0x26, + 0xA0, 0x39, 0x10, 0x69, 0x2A, 0xA4, 0xE1, 0x58, 0xF6, 0x81, 0xCB, 0xAA, 0x7C, 0x0F, 0xF8, 0x03, 0xD6, 0x66, 0x4B, 0x60, 0x9E, 0x5A, 0x4A, 0x25, 0x73, 0x58, 0x9F, 0xCD, 0x16, 0x8D, 0x17, 0x90, + 0x13, 0x32, 0x3E, 0x4B, 0x4F, 0x51, 0x53, 0x68, 0x6B, 0x74, 0x75, 0x78, 0x7C, 0xA2, 0xAF, 0xB6, 0xC4, 0xC5, 0xF4, 0xF8, 0x0D, 0x1D, 0x37, 0x46, 0x4D, 0x55, 0x57, 0x6A, 0x7B, 0x8C, 0xAC, 0xB2, + 0xC6, 0xC7, 0xC8, 0xD2, 0xEA, 0xF4, 0xF9, 0xFC, 0x18, 0x19, 0x20, 0x25, 0x27, 0x39, 0x5A, 0x5E, 0x90, 0xA4, 0xAF, 0xE8, 0xEF, 0xF2, 0xF8, 0xF9, 0x11, 0x29, 0x38, 0x68, 0x76, 0xAC, 0xAD, 0xBD, + 0xD6, 0xDA, 0xE1, 0xEB, 0xF3, 0x1B, 0x38, 0x5D, 0x67, 0x76, 0x81, 0x87, 0x8A, 0x91, 0x94, 0xAE, 0xC2, 0xD6, 0xD9, 0xDF, 0xFF, 0x01, 0x02, 0x1B, 0x2F, 0x34, 0x3B, 0x3F, 0x40, 0x58, 0x94, 0xAE, + 0xB1, 0xBD, 0xC5, 0xD5, 0xD7, 0x0A, 0x20, 0x23, 0x2D, 0x30, 0x3C, 0x65, 0x6C, 0x75, 0x76, 0x7E, 0x83, 0x90, 0xC2, 0xE7, 0xEB, 0x0C, 0x51, 0x64, 0x77, 0x88, 0xA4, 0xBB, 0xC1, 0xC7, 0xDB, 0xDC, + 0xE5, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, 0x28, 0x38, 0x45, 0x55, 0x65, 0x75, 0x81, 0x02, 0x10, 0x1C, 0x20, 0x18, 0x40, 0x08, 0x09, 0x06, 0x4C, 0x04, 0x04, + 0x02, 0x85, 0x00, 0x1D, 0xA0, 0x42, 0x9C, 0x48, 0x00, 0x81, 0x8C, 0x40, 0xC1, 0x42, 0x00, 0xC1, 0x0D, 0x09, 0x01, 0x94, 0xE8, 0x78, 0x5E, 0x1F, 0xF5, 0x65, 0x11, 0x03, + }, + }, + { + .name = "Dilithium Round 2, Level 5 (8-7) KAT 0", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_87, + .rho_len = 32, + .rho = { + 0x7C, 0x99, 0x35, 0xA0, 0xB0, 0x76, 0x94, 0xAA, 0x0C, 0x6D, 0x10, 0xE4, 0xDB, 0x6B, 0x1A, 0xDD, 0x2F, 0xD8, 0x1A, 0x25, 0xCC, 0xB1, 0x48, 0x03, 0x2D, 0xCD, 0x73, 0x99, 0x36, 0x73, 0x7F, 0x2D, + }, + .seed_len = 32, + .seed = { + 0x3E, 0x78, 0x4C, 0xCB, 0x7E, 0xBC, 0xDC, 0xFD, 0x45, 0x54, 0x2B, 0x7F, 0x6A, 0xF7, 0x78, 0x74, 0x2E, 0x0F, 0x44, 0x79, 0x17, 0x50, 0x84, 0xAA, 0x48, 0x8B, 0x3B, 0x74, 0x34, 0x06, 0x78, 0xAA, + }, + .tr_len = 48, + .tr = { + 0x89, 0xDB, 0xBF, 0xC3, 0x69, 0x33, 0x5D, 0x8F, 0x70, 0xE7, 0xBC, 0xB4, 0xD1, 0x66, 0xD4, 0xBD, 0xD0, 0xD8, 0x36, 0xE4, 0x5D, 0xE9, 0x37, 0x92, 0xED, 0xC4, 0x26, 0x10, 0x6F, 0xBF, 0x5A, 0xF2, + 0x7C, 0x68, 0xA9, 0x50, 0xB4, 0xA1, 0xA6, 0x42, 0x28, 0x01, 0xC6, 0xF2, 0xAC, 0xC3, 0xA9, 0xFA, + }, + .s1_len = 672, + .s1 = { + 0x91, 0xB4, 0x2D, 0xA1, 0x38, 0x24, 0x08, 0x19, 0x24, 0x1A, 0x30, 0x4D, 0x40, 0xA8, 0x6C, 0xD8, 0x04, 0x6A, 0x03, 0x28, 0x04, 0x41, 0x38, 0x22, 0x22, 0x39, 0x0A, 0xE2, 0x80, 0x0D, 0x12, 0x49, + 0x91, 0x24, 0xB4, 0x50, 0x93, 0x46, 0x89, 0xD1, 0x30, 0x4C, 0x04, 0x20, 0x24, 0x20, 0x20, 0x31, 0x59, 0x92, 0x41, 0xC3, 0x26, 0x61, 0x14, 0x47, 0x32, 0xDB, 0x12, 0x69, 0x63, 0x46, 0x01, 0x10, + 0x93, 0x91, 0x10, 0x39, 0x81, 0x5B, 0x26, 0x71, 0x40, 0xB0, 0x01, 0x03, 0x41, 0x48, 0x04, 0x19, 0x09, 0x13, 0xB4, 0x91, 0x0C, 0x46, 0x08, 0xD4, 0x08, 0x09, 0x0C, 0x99, 0x04, 0x00, 0x35, 0x61, + 0x13, 0x14, 0x4C, 0x19, 0x41, 0x28, 0x1C, 0x16, 0x80, 0x88, 0xA0, 0x29, 0x1A, 0x30, 0x02, 0x10, 0x80, 0x4C, 0x13, 0x43, 0x25, 0x04, 0x08, 0x81, 0x20, 0x43, 0x70, 0x14, 0x11, 0x6A, 0x99, 0x00, + 0x40, 0x48, 0x82, 0x31, 0x12, 0x42, 0x20, 0x48, 0x06, 0x0D, 0xE2, 0xA2, 0x0C, 0x82, 0xB0, 0x28, 0xE2, 0x36, 0x10, 0x49, 0x16, 0x84, 0xD8, 0x04, 0x4C, 0x51, 0xB8, 0x68, 0xC2, 0x84, 0x90, 0x9B, + 0x10, 0x31, 0x21, 0x49, 0x32, 0x94, 0x20, 0x0D, 0x04, 0x41, 0x24, 0xCB, 0xA4, 0x6D, 0x1A, 0x82, 0x61, 0x08, 0x40, 0x8E, 0xA4, 0x00, 0x44, 0x93, 0x92, 0x91, 0x8C, 0x30, 0x62, 0x60, 0xB2, 0x90, + 0x58, 0x40, 0x62, 0x11, 0x97, 0x31, 0x21, 0x11, 0x81, 0x0C, 0x28, 0x88, 0x09, 0x07, 0x42, 0x88, 0x40, 0x6C, 0xC0, 0x96, 0x28, 0x81, 0x28, 0x8A, 0xC0, 0x12, 0x0C, 0x93, 0x48, 0x4C, 0x89, 0x82, + 0x25, 0xD8, 0x00, 0x22, 0x24, 0x45, 0x41, 0x1B, 0x95, 0x2C, 0xA0, 0x92, 0x61, 0x84, 0xA2, 0x70, 0x59, 0x86, 0x10, 0x0B, 0x87, 0x08, 0x10, 0x98, 0x61, 0xD3, 0x40, 0x0D, 0x40, 0xB0, 0x8D, 0x09, + 0x05, 0x71, 0x60, 0x84, 0x70, 0x18, 0x80, 0x61, 0x1A, 0x16, 0x2E, 0x63, 0x32, 0x06, 0x80, 0x80, 0x88, 0x50, 0xC6, 0x8C, 0x00, 0x10, 0x24, 0xC1, 0x00, 0x26, 0x94, 0x90, 0x48, 0x44, 0xB6, 0x29, + 0x1A, 0x35, 0x48, 0xD3, 0xB0, 0x91, 0x21, 0xA4, 0x08, 0x11, 0x34, 0x32, 0x03, 0x01, 0x05, 0x21, 0x32, 0x46, 0x1B, 0x31, 0x31, 0x1B, 0x86, 0x0C, 0x1A, 0x28, 0x0D, 0xD1, 0x08, 0x28, 0x8B, 0xA8, + 0x0D, 0x98, 0x90, 0x05, 0xD0, 0xA8, 0x29, 0x83, 0x48, 0x71, 0x03, 0x33, 0x80, 0x24, 0x90, 0x68, 0xD1, 0xA0, 0x2C, 0x23, 0x10, 0x4D, 0x12, 0x95, 0x11, 0xE4, 0x14, 0x21, 0x14, 0x39, 0x4E, 0x12, + 0x01, 0x70, 0x0C, 0x25, 0x71, 0x24, 0x83, 0x89, 0x54, 0x30, 0x06, 0x11, 0x90, 0x45, 0x12, 0x03, 0x04, 0x59, 0xB0, 0x4C, 0x20, 0x36, 0x8A, 0x19, 0x30, 0x72, 0x98, 0x94, 0x4C, 0x14, 0x81, 0x40, + 0xA2, 0xC6, 0x84, 0xCB, 0xA2, 0x48, 0x0C, 0xC1, 0x2D, 0x8A, 0xC4, 0x05, 0x42, 0x94, 0x45, 0x5B, 0xB4, 0x08, 0xDB, 0x18, 0x24, 0x88, 0x20, 0x90, 0x1B, 0xC3, 0x50, 0xA1, 0x96, 0x4D, 0x0B, 0x31, + 0x6D, 0x93, 0x26, 0x46, 0x00, 0x35, 0x52, 0x01, 0x13, 0x42, 0xDA, 0x46, 0x6A, 0x1A, 0x34, 0x01, 0x40, 0x92, 0x41, 0xC0, 0x08, 0x66, 0xE3, 0x94, 0x01, 0x63, 0x28, 0x69, 0x0C, 0x25, 0x31, 0x0B, + 0x21, 0x24, 0x43, 0xA2, 0x30, 0xD3, 0x22, 0x44, 0xCB, 0x36, 0x71, 0x02, 0x02, 0x42, 0x1A, 0xC1, 0x2C, 0x20, 0x23, 0x80, 0x8B, 0xA8, 0x85, 0x88, 0x08, 0x4A, 0x94, 0x10, 0x48, 0x18, 0x81, 0x29, + 0xE2, 0xB4, 0x4C, 0x89, 0x88, 0x51, 0xC9, 0x06, 0x09, 0xD3, 0x96, 0x71, 0x54, 0xB0, 0x91, 0x53, 0x86, 0x04, 0x53, 0xC4, 0x44, 0x81, 0x98, 0x11, 0x88, 0x20, 0x04, 0xA0, 0x16, 0x0A, 0x49, 0xA0, + 0x10, 0x1A, 0x17, 0x44, 0x21, 0x26, 0x66, 0xE0, 0xC0, 0x09, 0x59, 0x90, 0x8C, 0x93, 0x10, 0x49, 0x00, 0x85, 0x65, 0x4C, 0xC6, 0x0D, 0x00, 0x18, 0x30, 0x1B, 0x12, 0x6E, 0x10, 0x02, 0x45, 0xA2, + 0x12, 0x49, 0x22, 0xC8, 0x20, 0x03, 0xC5, 0x48, 0x12, 0x04, 0x52, 0xA1, 0x88, 0x25, 0x40, 0xB2, 0x4D, 0x4B, 0x38, 0x28, 0x23, 0xB2, 0x64, 0xC2, 0x38, 0x90, 0x09, 0x46, 0x92, 0x0C, 0x90, 0x0D, + 0x04, 0x06, 0x0C, 0x4C, 0x16, 0x2D, 0x08, 0x10, 0x49, 0x20, 0x47, 0x65, 0x50, 0x28, 0x29, 0x1A, 0x88, 0x80, 0x40, 0x30, 0x6D, 0x88, 0x36, 0x70, 0x63, 0x98, 0x71, 0x99, 0x96, 0x2C, 0x1B, 0x91, + 0x61, 0x61, 0x40, 0x06, 0x13, 0x35, 0x04, 0x09, 0x08, 0x8E, 0x54, 0xB8, 0x44, 0x81, 0x30, 0x08, 0xC8, 0x10, 0x2C, 0x5A, 0xB0, 0x04, 0x42, 0x46, 0x61, 0x20, 0x03, 0x88, 0x91, 0xA0, 0x91, 0x81, + 0x10, 0x4D, 0x12, 0xB7, 0x81, 0x20, 0x42, 0x02, 0x54, 0x94, 0x24, 0x59, 0xC4, 0x25, 0x8C, 0x44, 0x70, 0xE3, 0x32, 0x8E, 0x9A, 0x02, 0x60, 0xE4, 0xA6, 0x21, 0x4A, 0xB2, 0x85, 0x93, 0x36, 0x20, + }, + .s2_len = 768, + .s2 = { + 0x01, 0x05, 0x32, 0x11, 0x44, 0x66, 0xE2, 0x06, 0x40, 0x14, 0x49, 0x6C, 0x0B, 0x86, 0x80, 0x02, 0x47, 0x26, 0xD2, 0xB2, 0x25, 0x58, 0x48, 0x0E, 0x58, 0x44, 0x11, 0xD1, 0x44, 0x50, 0x51, 0xB8, + 0x81, 0xC4, 0xA0, 0x48, 0x10, 0xC9, 0x50, 0x08, 0x98, 0x88, 0xD8, 0x28, 0x2A, 0x52, 0xC0, 0x4D, 0xD1, 0x38, 0x12, 0xD8, 0x46, 0x89, 0x00, 0x94, 0x00, 0xDA, 0xC4, 0x45, 0x9B, 0x44, 0x6E, 0x0B, + 0x44, 0x0C, 0xC0, 0xC0, 0x01, 0x20, 0xC1, 0x0C, 0xC0, 0x04, 0x4C, 0x08, 0x24, 0x21, 0x23, 0xC7, 0x65, 0x03, 0xA0, 0x80, 0x91, 0xC2, 0x50, 0x21, 0x10, 0x31, 0x99, 0x36, 0x00, 0x64, 0x28, 0x70, + 0x81, 0x38, 0x05, 0x4A, 0x18, 0x80, 0x1C, 0x89, 0x24, 0x08, 0x95, 0x49, 0x24, 0x39, 0x40, 0x24, 0x15, 0x22, 0xD9, 0x32, 0x90, 0x23, 0x24, 0x71, 0xC4, 0x46, 0x50, 0xCB, 0x86, 0x65, 0xE4, 0x94, + 0x8C, 0x42, 0x04, 0x82, 0x8A, 0x86, 0x71, 0x13, 0xA3, 0x00, 0xDB, 0x44, 0x04, 0x23, 0x82, 0x10, 0x23, 0x46, 0x26, 0x0B, 0x08, 0x08, 0x60, 0x16, 0x11, 0xA4, 0xB6, 0x24, 0xE1, 0x32, 0x69, 0x04, + 0x17, 0x86, 0xE3, 0x84, 0x2C, 0x9C, 0x32, 0x41, 0x92, 0xC8, 0x61, 0x5A, 0x32, 0x26, 0x24, 0xC3, 0x29, 0x5A, 0xC8, 0x05, 0x0A, 0x06, 0x8E, 0xE1, 0x16, 0x20, 0x99, 0x94, 0x61, 0x19, 0xA2, 0x0C, + 0x1B, 0x05, 0x2E, 0x1B, 0x44, 0x64, 0x9A, 0x00, 0x84, 0x8C, 0x18, 0x52, 0x84, 0xB4, 0x60, 0x82, 0x20, 0x08, 0x42, 0x48, 0x09, 0x84, 0x08, 0x46, 0x11, 0x00, 0x46, 0x13, 0x43, 0x01, 0xE1, 0x06, + 0x91, 0x1B, 0x44, 0x8E, 0x01, 0x94, 0x64, 0x4A, 0x12, 0x09, 0x98, 0x38, 0x0E, 0xE4, 0x06, 0x25, 0x24, 0x13, 0x68, 0x13, 0x21, 0x06, 0x04, 0xB9, 0x40, 0x54, 0x24, 0x25, 0x14, 0x88, 0x69, 0x82, + 0x38, 0x01, 0xA4, 0x28, 0x72, 0x50, 0x86, 0x61, 0x23, 0xB1, 0x88, 0xA2, 0x90, 0x08, 0x1C, 0x95, 0x30, 0x1C, 0x40, 0x82, 0x49, 0xC8, 0x64, 0xCA, 0x04, 0x40, 0x44, 0x98, 0x21, 0x0B, 0x24, 0x61, + 0x1C, 0xA0, 0x4C, 0x09, 0xA4, 0x21, 0xC9, 0x08, 0x8A, 0x22, 0x13, 0x41, 0x80, 0xC8, 0x89, 0x23, 0xB1, 0x64, 0x1C, 0x11, 0x49, 0x40, 0xA2, 0x29, 0x61, 0xC8, 0x8C, 0x8B, 0x96, 0x91, 0x83, 0x02, + 0x42, 0xE1, 0xB6, 0x85, 0x51, 0x86, 0x4C, 0x04, 0x43, 0x91, 0x4B, 0xB8, 0x69, 0x50, 0x24, 0x81, 0xC8, 0x04, 0x2E, 0x1B, 0xB9, 0x31, 0x93, 0x24, 0x00, 0x23, 0x86, 0x81, 0xC2, 0xB8, 0x61, 0x09, + 0x00, 0x62, 0x14, 0x99, 0x41, 0x19, 0x37, 0x6E, 0x1C, 0x16, 0x30, 0x0A, 0x27, 0x45, 0x51, 0x10, 0x0D, 0x1C, 0x33, 0x4A, 0x10, 0x40, 0x80, 0xA0, 0x34, 0x62, 0xD8, 0x44, 0x4A, 0x01, 0x06, 0x45, + 0x23, 0x83, 0x8C, 0x24, 0xA4, 0x85, 0x01, 0x04, 0x0C, 0x09, 0x03, 0x32, 0xDB, 0x90, 0x09, 0x4A, 0x14, 0x42, 0x01, 0x08, 0x21, 0x22, 0x08, 0x66, 0x8B, 0x28, 0x70, 0x24, 0x38, 0x31, 0x0C, 0x46, + 0x69, 0x43, 0x44, 0x69, 0x9A, 0x34, 0x4D, 0x82, 0xC8, 0x40, 0x42, 0x42, 0x01, 0x23, 0xC7, 0x29, 0x91, 0x32, 0x72, 0x1B, 0x36, 0x4C, 0x1B, 0x33, 0x05, 0x13, 0x35, 0x61, 0x14, 0x02, 0x46, 0x08, + 0x03, 0x65, 0x21, 0x87, 0x20, 0x09, 0x03, 0x91, 0xC1, 0xC4, 0x25, 0xE2, 0xA6, 0x4C, 0x81, 0x14, 0x48, 0x20, 0x25, 0x4D, 0x03, 0x19, 0x69, 0xA3, 0x00, 0x69, 0x54, 0xA8, 0x30, 0x9C, 0x86, 0x05, + 0x9C, 0x36, 0x82, 0x03, 0x37, 0x0C, 0x0A, 0x15, 0x50, 0x9C, 0xC0, 0x91, 0x04, 0xB6, 0x91, 0x0C, 0x11, 0x80, 0x09, 0xB5, 0x70, 0x63, 0x20, 0x92, 0x44, 0x22, 0x71, 0xC1, 0x48, 0x44, 0x98, 0xC4, + 0x6D, 0x64, 0xA6, 0x89, 0x0A, 0xA9, 0x40, 0x04, 0xB8, 0x50, 0x04, 0x34, 0x8C, 0xE2, 0xC4, 0x80, 0x02, 0x00, 0x12, 0xA3, 0x36, 0x46, 0xD2, 0x00, 0x01, 0x1C, 0x45, 0x46, 0x22, 0x33, 0x6D, 0x81, + 0x92, 0x01, 0x08, 0x12, 0x86, 0x9C, 0x04, 0x51, 0xA3, 0x98, 0x30, 0x48, 0x10, 0x91, 0x19, 0xA0, 0x44, 0xC3, 0x04, 0x8D, 0x42, 0x90, 0x40, 0x43, 0x80, 0x44, 0xA4, 0x46, 0x71, 0x0B, 0xA2, 0x60, + 0x52, 0x18, 0x6D, 0x0B, 0xB6, 0x85, 0x1B, 0xB2, 0x0C, 0x94, 0x12, 0x09, 0x04, 0xB6, 0x41, 0x18, 0xA8, 0x84, 0x10, 0x00, 0x22, 0x53, 0x42, 0x69, 0xC3, 0xA8, 0x81, 0x00, 0x25, 0x32, 0x81, 0x16, + 0x28, 0x81, 0x44, 0x2D, 0xD4, 0xB4, 0x4D, 0x08, 0xC8, 0x45, 0x5A, 0x04, 0x01, 0xC1, 0x90, 0x50, 0x22, 0x14, 0x82, 0x63, 0xC6, 0x6D, 0x04, 0x22, 0x72, 0x1C, 0xB9, 0x44, 0x9B, 0x46, 0x0D, 0xC2, + 0x14, 0x22, 0x91, 0xB0, 0x44, 0x21, 0x89, 0x68, 0xC4, 0x96, 0x08, 0x0A, 0xB9, 0x8C, 0x22, 0xB9, 0x40, 0xE2, 0x26, 0x50, 0x8C, 0x88, 0x25, 0xCB, 0xB8, 0x04, 0x54, 0x16, 0x25, 0x63, 0x34, 0x0C, + 0x24, 0xB0, 0x29, 0xA3, 0x44, 0x20, 0x43, 0x46, 0x40, 0x9C, 0x02, 0x48, 0x5A, 0xC8, 0x2C, 0x00, 0x05, 0x31, 0x09, 0x18, 0x00, 0xDB, 0x46, 0x51, 0xD2, 0xB6, 0x2C, 0x44, 0x40, 0x88, 0x9A, 0x96, + 0x24, 0x12, 0xA5, 0x90, 0x04, 0x39, 0x86, 0x10, 0x80, 0x2D, 0x10, 0x99, 0x21, 0x60, 0x06, 0x66, 0x21, 0x89, 0x4C, 0x91, 0x04, 0x60, 0x23, 0xB9, 0x01, 0x12, 0x11, 0x48, 0x12, 0x29, 0x51, 0xA1, + 0x06, 0x45, 0x44, 0x22, 0x12, 0x03, 0x27, 0x8E, 0x23, 0x94, 0x84, 0x0C, 0x29, 0x06, 0x94, 0x86, 0x50, 0xE0, 0x48, 0x10, 0x24, 0x26, 0x40, 0x61, 0x04, 0x66, 0x9C, 0xB2, 0x84, 0x54, 0xC2, 0x2C, + }, + .t0_len = 3584, + .t0 = { + 0xD6, 0xD4, 0x27, 0x24, 0xCA, 0xFD, 0xF2, 0x81, 0xB9, 0xCA, 0xDC, 0x58, 0x04, 0x84, 0x83, 0x95, 0x49, 0x25, 0x4C, 0x9B, 0xE0, 0xA1, 0xF9, 0xAA, 0x9D, 0x76, 0xE6, 0x54, 0x63, 0xCD, 0x83, 0x14, + 0x20, 0x65, 0xE7, 0xF7, 0x47, 0xBD, 0x27, 0x4C, 0xF3, 0x7E, 0x85, 0x70, 0xE0, 0xE6, 0x3A, 0xDB, 0xF8, 0x5F, 0x31, 0x79, 0x14, 0x75, 0xFF, 0x1A, 0x2F, 0x50, 0x5B, 0x53, 0x24, 0x77, 0x2C, 0xB0, + 0xEB, 0x21, 0x9E, 0x2C, 0x28, 0xC4, 0xEF, 0xBC, 0x31, 0xE7, 0x13, 0xDF, 0x18, 0x77, 0x25, 0xB7, 0xBD, 0xE2, 0x90, 0xE6, 0x08, 0x98, 0x5B, 0x7D, 0x8A, 0x71, 0x14, 0x42, 0xD4, 0x03, 0xD2, 0x56, + 0xF5, 0x35, 0xA4, 0x27, 0x1F, 0x6C, 0xC6, 0x5F, 0x91, 0xF1, 0xA7, 0x3F, 0x3B, 0x33, 0x94, 0x83, 0x3D, 0xF0, 0x12, 0x79, 0xDC, 0x71, 0xFB, 0x60, 0xBD, 0x14, 0x13, 0xBF, 0x23, 0xBA, 0x3A, 0x20, + 0xC7, 0x15, 0xC1, 0x30, 0xDA, 0x19, 0x2D, 0x05, 0x1F, 0xF6, 0xEA, 0x7E, 0xDD, 0xBB, 0x81, 0xDB, 0xC4, 0xBE, 0xBA, 0xF6, 0x71, 0x41, 0x23, 0x6E, 0x5D, 0x9E, 0x09, 0x93, 0xFB, 0x7D, 0xC7, 0x06, + 0x44, 0x83, 0xDA, 0x06, 0x99, 0xE8, 0x40, 0x21, 0x76, 0xC6, 0xB2, 0x0F, 0x24, 0x0D, 0x35, 0x87, 0xBC, 0x1B, 0x07, 0x3C, 0x9A, 0xA0, 0x09, 0xCB, 0xC1, 0xB0, 0x5F, 0x49, 0xCC, 0xBB, 0x25, 0x13, + 0x12, 0x96, 0x92, 0xDF, 0x1C, 0xEC, 0xDA, 0x29, 0x54, 0xCC, 0xEC, 0xC1, 0x7B, 0xBB, 0x1D, 0x11, 0x96, 0x4F, 0xAE, 0xB0, 0xF9, 0xE0, 0x29, 0x21, 0x29, 0x59, 0xB6, 0x8E, 0x4B, 0xE0, 0x66, 0x64, + 0xF9, 0x58, 0x74, 0x32, 0xC0, 0x2D, 0xE6, 0x15, 0x88, 0x51, 0x55, 0x57, 0x56, 0x5A, 0x26, 0xA6, 0xEC, 0xD6, 0xB4, 0xDE, 0x47, 0xF0, 0xB6, 0x47, 0x63, 0x77, 0x81, 0xEC, 0x19, 0x49, 0x32, 0xD2, + 0x82, 0xFF, 0x1F, 0x83, 0x5E, 0xB8, 0x09, 0x66, 0xAB, 0xA2, 0x16, 0xB4, 0xE7, 0xF8, 0x8E, 0xAB, 0x97, 0x05, 0x21, 0x26, 0x4D, 0xB5, 0xD6, 0xF2, 0x83, 0xA4, 0xF6, 0x79, 0x1E, 0x32, 0x9F, 0xB8, + 0xCB, 0x54, 0x25, 0xB9, 0x13, 0x9E, 0x96, 0xAB, 0xB3, 0x94, 0x4E, 0x35, 0xBB, 0x88, 0x64, 0x2A, 0xC0, 0xE7, 0xDC, 0xDA, 0xB9, 0xB5, 0x59, 0xD0, 0x9E, 0x29, 0x55, 0x72, 0xB2, 0x52, 0x92, 0xC0, + 0x3C, 0xD5, 0xAB, 0x5E, 0x7B, 0xBE, 0x77, 0x61, 0xD8, 0x58, 0x3F, 0xAD, 0x91, 0x66, 0x91, 0x3F, 0xDE, 0x1B, 0x65, 0x8F, 0x87, 0x26, 0xC3, 0xF7, 0xE6, 0xD2, 0x65, 0x63, 0x17, 0xDA, 0xAF, 0xB9, + 0x2E, 0x78, 0x7D, 0x24, 0xC5, 0xD8, 0x94, 0x7F, 0xF5, 0x95, 0xA5, 0x85, 0x3D, 0x61, 0x11, 0x73, 0xDF, 0x20, 0xF0, 0xAE, 0x01, 0x50, 0x75, 0x8C, 0x6B, 0x13, 0x1D, 0xFD, 0xEF, 0x36, 0xA0, 0x1D, + 0x7C, 0x87, 0x4D, 0x0B, 0x8C, 0xD0, 0xC2, 0x53, 0x83, 0x56, 0x94, 0x06, 0xCB, 0xE4, 0x2A, 0x72, 0xD7, 0x09, 0x7E, 0x84, 0xD9, 0x82, 0x58, 0x39, 0xEB, 0xD1, 0x4F, 0x17, 0x5E, 0xD5, 0x1E, 0x6A, + 0xC1, 0xA3, 0xF7, 0xF7, 0xBE, 0xFF, 0x60, 0xF5, 0xC0, 0x72, 0x73, 0x42, 0xD7, 0xDD, 0x34, 0x76, 0xDC, 0x9A, 0xE0, 0xE2, 0x7E, 0xDB, 0xB8, 0x86, 0xBF, 0xA0, 0x0D, 0x36, 0xFE, 0x80, 0xDA, 0x81, + 0x6A, 0x45, 0xE0, 0xC8, 0x00, 0x0B, 0x6E, 0x23, 0xE9, 0xB5, 0xCA, 0xD0, 0x13, 0xB6, 0xDE, 0xBF, 0x74, 0x9E, 0xB7, 0x27, 0xB8, 0xD8, 0x3B, 0xFE, 0x26, 0xF6, 0xC5, 0x99, 0xD5, 0xBD, 0x45, 0xB5, + 0x82, 0xB8, 0x4F, 0x4F, 0xC8, 0x34, 0x10, 0xEE, 0x2A, 0x67, 0x5C, 0x66, 0x14, 0x5F, 0x52, 0xCF, 0x36, 0x83, 0x29, 0x0C, 0xC7, 0x2A, 0x29, 0x28, 0x5D, 0x70, 0x66, 0x7A, 0x3A, 0x31, 0x58, 0x93, + 0x54, 0xD9, 0x19, 0x31, 0x62, 0x5F, 0xFA, 0xCF, 0xB7, 0xE0, 0x2C, 0x03, 0xFE, 0x48, 0x09, 0x2A, 0x12, 0x0E, 0x5F, 0x43, 0x12, 0x76, 0xE8, 0x37, 0x4D, 0xBE, 0x15, 0x40, 0x96, 0xC8, 0x6C, 0x58, + 0x79, 0x10, 0xF5, 0x05, 0x1A, 0x86, 0x14, 0x17, 0xC0, 0x6A, 0x73, 0x48, 0x0C, 0xE3, 0x19, 0x5C, 0xC9, 0x99, 0xF6, 0xB8, 0xB3, 0x01, 0x9B, 0x22, 0x37, 0x96, 0xC5, 0xE1, 0x1F, 0x73, 0x42, 0xC9, + 0x74, 0x6A, 0xED, 0xBF, 0xA9, 0x44, 0xCD, 0x79, 0xB8, 0x5C, 0x10, 0x00, 0x07, 0xBB, 0x58, 0x69, 0x84, 0x3A, 0x23, 0xAD, 0x06, 0xD8, 0x1F, 0x5C, 0xB2, 0x9D, 0xD1, 0x7B, 0xCE, 0xE7, 0x55, 0x72, + 0xB9, 0xE0, 0xCF, 0xDB, 0xD5, 0xA8, 0x3A, 0x30, 0x57, 0x44, 0x2D, 0xF0, 0x00, 0xDA, 0x7A, 0x3A, 0xA6, 0xFC, 0x5F, 0xB2, 0x89, 0xA1, 0x29, 0x99, 0x24, 0xD9, 0x23, 0x1F, 0xE1, 0xD0, 0xCF, 0x3C, + 0x17, 0xF1, 0x80, 0x3F, 0x61, 0x43, 0xC0, 0x97, 0xF9, 0x54, 0x2C, 0x9A, 0xBB, 0x8F, 0x98, 0x77, 0xE4, 0xAE, 0xC5, 0x4A, 0xB9, 0x39, 0x93, 0xDC, 0x49, 0x87, 0xDF, 0x67, 0x80, 0x8B, 0xF7, 0xBE, + 0xDE, 0xA8, 0x6B, 0x5C, 0x83, 0xD2, 0x48, 0xE9, 0x5E, 0xA3, 0x02, 0x45, 0x3F, 0x5F, 0x6B, 0x7F, 0xF5, 0xB5, 0xF5, 0x8B, 0x65, 0xD9, 0x32, 0xD2, 0xBF, 0x73, 0x7C, 0x51, 0x89, 0x3D, 0x89, 0xF0, + 0x7D, 0xA5, 0xBF, 0xEA, 0x79, 0xD7, 0xE7, 0xFB, 0x2A, 0xAB, 0x82, 0x33, 0xA2, 0x7E, 0xB4, 0x4C, 0x68, 0x58, 0x05, 0x1D, 0x92, 0xB9, 0x98, 0xBC, 0x47, 0x51, 0xA4, 0x90, 0x2A, 0xA2, 0x22, 0xDE, + 0x2D, 0x5C, 0xDC, 0xEC, 0x26, 0xB3, 0x6D, 0xBA, 0x47, 0xCC, 0xEB, 0x41, 0xFB, 0x19, 0x2D, 0xDF, 0xFD, 0x55, 0x12, 0xD8, 0x2B, 0x1B, 0xD3, 0x4D, 0x1E, 0xAA, 0x42, 0xF8, 0xCC, 0x50, 0x3F, 0x23, + 0x85, 0x92, 0x42, 0x07, 0x9C, 0xBC, 0x1A, 0x55, 0xF0, 0x95, 0xAB, 0xB3, 0xC1, 0x87, 0x9F, 0xD1, 0xB4, 0x85, 0x04, 0xD8, 0x05, 0x4C, 0x15, 0xEB, 0x3E, 0xBF, 0x54, 0xA3, 0x2C, 0x5B, 0x62, 0xC0, + 0x55, 0x55, 0xE4, 0xAC, 0x60, 0x36, 0x91, 0x9B, 0xB9, 0xA1, 0xBB, 0x53, 0x9E, 0x78, 0x86, 0x7A, 0x74, 0xF5, 0x3C, 0x23, 0xB1, 0xA1, 0x35, 0x98, 0x7D, 0x8B, 0xDD, 0x63, 0xE0, 0x92, 0xAB, 0x2B, + 0xF1, 0xD8, 0xF6, 0x60, 0x38, 0xE1, 0x49, 0xAE, 0x41, 0x0B, 0x09, 0xAB, 0x25, 0xB4, 0xFE, 0x65, 0x53, 0xB3, 0x0E, 0x7B, 0xA7, 0xBF, 0x01, 0x36, 0x36, 0x8E, 0x3B, 0x8B, 0x73, 0x23, 0xA1, 0x24, + 0x89, 0x02, 0x94, 0x7B, 0x2A, 0x39, 0x85, 0xB5, 0xC5, 0xCB, 0x80, 0x27, 0xAE, 0xF8, 0xA9, 0xE3, 0x42, 0xA3, 0xB7, 0x54, 0x3C, 0x31, 0x54, 0x72, 0x49, 0xFC, 0x77, 0x7C, 0x59, 0x2A, 0x31, 0xB8, + 0x5B, 0x4B, 0x07, 0xE0, 0xAD, 0x87, 0x61, 0x2C, 0x3D, 0xF4, 0x9B, 0x9E, 0xB6, 0x6A, 0x53, 0xF4, 0x11, 0xC6, 0xD6, 0xDE, 0x9F, 0x26, 0x86, 0x95, 0x07, 0x74, 0x80, 0x6A, 0xD0, 0xCE, 0xBF, 0x25, + 0x4C, 0x18, 0x2F, 0x3A, 0x5D, 0xF9, 0xE4, 0x29, 0xF0, 0x79, 0x2E, 0x96, 0x35, 0x95, 0xB8, 0x42, 0x6B, 0xB0, 0xCB, 0x53, 0x62, 0x75, 0x36, 0x26, 0x5C, 0x4F, 0x63, 0x46, 0xB4, 0xB0, 0x72, 0xEA, + 0xB4, 0xD1, 0xE6, 0x87, 0xA4, 0xDE, 0x7B, 0x82, 0x89, 0x90, 0xEB, 0xF3, 0x38, 0x1F, 0x0B, 0x70, 0xE9, 0x26, 0xD6, 0x7B, 0x76, 0x89, 0x73, 0xF1, 0x02, 0x40, 0x80, 0xBD, 0x40, 0xC6, 0x7B, 0x81, + 0x04, 0x09, 0x34, 0xD1, 0xC3, 0xC3, 0x77, 0x4D, 0xDE, 0x93, 0x28, 0xBE, 0x69, 0xBB, 0xD5, 0xDF, 0xE3, 0xF2, 0x80, 0xDB, 0x77, 0xFF, 0xC1, 0xA7, 0x8D, 0x11, 0x13, 0x34, 0xB4, 0x21, 0x97, 0x00, + 0x2B, 0xD8, 0x5C, 0xD7, 0xCD, 0xF7, 0xCB, 0xB6, 0xED, 0x3F, 0x41, 0xCB, 0xB9, 0xAD, 0x48, 0x1F, 0x44, 0xA3, 0x35, 0x11, 0x55, 0xA5, 0x22, 0x35, 0x0A, 0x65, 0x8F, 0x69, 0x92, 0x11, 0xD7, 0xAA, + 0x5E, 0x68, 0xA5, 0x27, 0x94, 0x76, 0xC0, 0x0B, 0xD9, 0xEE, 0x01, 0x0C, 0xEC, 0x6E, 0x51, 0x02, 0xD2, 0x70, 0x54, 0xC9, 0x74, 0xD1, 0x6B, 0xE4, 0xA6, 0xC6, 0x85, 0x99, 0xAE, 0x83, 0x01, 0x9C, + 0xB1, 0x32, 0x4E, 0x35, 0x10, 0x4F, 0x10, 0x5A, 0x59, 0xE6, 0xCF, 0x07, 0x67, 0x30, 0xF3, 0x3A, 0x03, 0xED, 0xD7, 0xC9, 0x2E, 0x07, 0x36, 0xB5, 0x42, 0x98, 0x79, 0x0C, 0xA8, 0xD5, 0x28, 0x72, + 0x74, 0x28, 0x23, 0x73, 0x19, 0x9E, 0x90, 0xB9, 0x49, 0x13, 0xB9, 0x9C, 0x06, 0xD7, 0xD5, 0xB6, 0xC4, 0x18, 0xF5, 0x5B, 0x66, 0x14, 0x13, 0x31, 0x13, 0x0E, 0x6B, 0xD5, 0x61, 0x52, 0xB8, 0xDB, + 0x19, 0xB2, 0xFB, 0x1B, 0xB6, 0x5C, 0x8D, 0x21, 0xFC, 0xD4, 0xBE, 0x45, 0x1A, 0x4A, 0x1C, 0x0F, 0xEE, 0x73, 0xDB, 0xC3, 0x55, 0x7D, 0x36, 0x2C, 0x45, 0x3D, 0x8E, 0x6A, 0x43, 0xE9, 0x9E, 0x47, + 0x97, 0xD1, 0xF2, 0x5B, 0x1A, 0x58, 0x98, 0x14, 0x81, 0x1D, 0x66, 0xB7, 0x31, 0xA7, 0x5E, 0x99, 0x3F, 0xF1, 0xD3, 0xBC, 0x42, 0x11, 0xF8, 0xC1, 0x51, 0x0B, 0x90, 0x40, 0x50, 0x68, 0x94, 0xB8, + 0x6B, 0xA9, 0xFB, 0xA3, 0x55, 0x49, 0x61, 0xDF, 0x34, 0xFD, 0xB7, 0x65, 0x5F, 0xD9, 0x28, 0x37, 0x8B, 0x4E, 0x65, 0x00, 0x14, 0x77, 0xD1, 0xFC, 0xF1, 0x8C, 0xB7, 0x1C, 0x5E, 0x41, 0x71, 0x69, + 0x6F, 0x33, 0xB2, 0xB6, 0x76, 0x30, 0x38, 0xD5, 0x12, 0xAC, 0xB0, 0xF7, 0xFE, 0xEE, 0x76, 0xF0, 0xFB, 0x16, 0x4E, 0x30, 0xFE, 0xB7, 0xD6, 0x37, 0xB3, 0xAB, 0x1E, 0x7F, 0x25, 0x1E, 0xF8, 0xC0, + 0x54, 0x31, 0x46, 0x1C, 0x3A, 0xB9, 0x0F, 0x05, 0x7D, 0xA0, 0xF4, 0xD8, 0xC3, 0xB3, 0x78, 0x7A, 0xE5, 0x8C, 0xB0, 0x13, 0x6D, 0x68, 0xAC, 0xB6, 0x40, 0x7B, 0xCF, 0x67, 0x16, 0x20, 0x72, 0x3A, + 0x02, 0x30, 0xD4, 0xF7, 0xDD, 0x7A, 0xDE, 0x77, 0x0C, 0x41, 0x8F, 0xCA, 0xD9, 0x97, 0x8F, 0x7C, 0x96, 0x22, 0x26, 0xCA, 0x6D, 0x65, 0x79, 0xBA, 0xDC, 0x67, 0x52, 0x23, 0x7C, 0x99, 0xD2, 0x4C, + 0xA8, 0x04, 0xE9, 0xF1, 0xFC, 0xDC, 0x9A, 0xAA, 0x11, 0x1F, 0x2C, 0x90, 0x5E, 0xF0, 0x31, 0x69, 0x0D, 0x17, 0x65, 0xE8, 0x21, 0x93, 0x8A, 0x0B, 0x78, 0x46, 0xC3, 0xBB, 0x80, 0xDB, 0xEF, 0x95, + 0x30, 0xC6, 0x8C, 0xAA, 0x0A, 0xDA, 0x96, 0x2A, 0x59, 0x5F, 0xD9, 0xE7, 0xAB, 0xD9, 0xE1, 0xF7, 0x6F, 0xF2, 0x97, 0xE1, 0x78, 0x50, 0x54, 0x13, 0xEE, 0x95, 0xFC, 0x0A, 0x95, 0x8D, 0x72, 0x0C, + 0x2A, 0x23, 0x86, 0xA1, 0x64, 0x50, 0xF9, 0x7D, 0xE5, 0x8E, 0xE2, 0x27, 0xBF, 0xA3, 0x3C, 0xAA, 0xC0, 0x3F, 0x13, 0x5A, 0x83, 0x45, 0x46, 0x9F, 0x26, 0xC7, 0x70, 0x26, 0x91, 0x5E, 0xE2, 0x0F, + 0xBD, 0x82, 0xB0, 0x9B, 0x02, 0xFE, 0xA7, 0x7A, 0xBC, 0xFB, 0x9D, 0xA8, 0x94, 0xD8, 0x67, 0x6E, 0x16, 0x0F, 0x1E, 0x1C, 0xEA, 0x42, 0x0B, 0x2C, 0xFE, 0x14, 0xFF, 0x08, 0xE1, 0x65, 0x0D, 0x56, + 0x5B, 0x6C, 0xDF, 0x6A, 0xD7, 0xEE, 0x51, 0x3D, 0xC1, 0xE7, 0x34, 0x30, 0x96, 0xDD, 0x26, 0x5C, 0x45, 0x9F, 0xA1, 0x7C, 0x55, 0xE5, 0xD6, 0xC6, 0x38, 0x28, 0xBC, 0xC4, 0xB7, 0x2A, 0x2A, 0x02, + 0x7C, 0x31, 0xD2, 0x43, 0x8A, 0x7B, 0xFF, 0x42, 0x77, 0x3F, 0xED, 0x94, 0x35, 0xC3, 0xC6, 0xED, 0x66, 0x4D, 0x35, 0x41, 0x86, 0x58, 0xCB, 0x13, 0x37, 0x43, 0xF4, 0x82, 0x73, 0x2F, 0x6F, 0xB2, + 0xC8, 0x9C, 0x68, 0x00, 0x05, 0x20, 0x9D, 0xFB, 0xEE, 0xAB, 0x70, 0x2A, 0x39, 0x11, 0xA8, 0x7D, 0xD5, 0x5E, 0xF3, 0x9F, 0x40, 0x93, 0x70, 0xBE, 0x94, 0x88, 0x84, 0x42, 0xB0, 0x8D, 0xB3, 0x37, + 0x08, 0xBC, 0xB3, 0x1A, 0x14, 0x07, 0x30, 0x3B, 0x4F, 0xED, 0xF3, 0x11, 0xC1, 0x52, 0x63, 0x57, 0x9F, 0x81, 0x74, 0x6C, 0xED, 0xFB, 0x79, 0x0C, 0xA0, 0x30, 0x4C, 0x88, 0xFC, 0xCA, 0x59, 0x56, + 0xE9, 0xF8, 0x19, 0xFE, 0xFF, 0xAC, 0x13, 0xC6, 0x4D, 0x96, 0xC4, 0x3C, 0x98, 0xD8, 0x8F, 0xEC, 0x8F, 0xD9, 0x83, 0xC1, 0xC5, 0x19, 0xCB, 0x88, 0x4D, 0x2E, 0x7A, 0x90, 0xCD, 0xF3, 0x65, 0xFE, + 0x5F, 0xB5, 0xDA, 0x8F, 0xAB, 0x74, 0xF0, 0x73, 0xBA, 0x25, 0x8D, 0x26, 0x4F, 0x94, 0x2D, 0x14, 0xD6, 0xE2, 0xE9, 0x08, 0x29, 0xAE, 0x35, 0x74, 0x6D, 0x05, 0x7A, 0x18, 0x0E, 0x56, 0x38, 0x42, + 0xF5, 0x4C, 0x4B, 0xC7, 0xD5, 0x00, 0x49, 0x43, 0x24, 0x72, 0xD1, 0xED, 0xF1, 0x38, 0xF2, 0xE5, 0x86, 0x26, 0xAB, 0x8C, 0x96, 0xE6, 0x00, 0xED, 0x19, 0x36, 0xF3, 0x38, 0x80, 0xF4, 0xF2, 0x20, + 0x1B, 0x61, 0x07, 0xC4, 0xEF, 0xB9, 0xC0, 0x2E, 0xCF, 0x31, 0x44, 0xE3, 0xAC, 0x55, 0xB0, 0xEE, 0x51, 0x68, 0xA7, 0x93, 0xB1, 0x5D, 0xB4, 0xA6, 0x1B, 0xFF, 0xFC, 0x8B, 0xE4, 0xA3, 0x80, 0x40, + 0xA0, 0x6C, 0x31, 0xF5, 0x15, 0x2D, 0x7C, 0x95, 0xF8, 0xC4, 0x94, 0x45, 0x12, 0x4D, 0x07, 0x20, 0x95, 0xFC, 0x14, 0xF6, 0x79, 0xDF, 0x55, 0xDC, 0x1E, 0x7F, 0xBE, 0x48, 0x83, 0xDA, 0xA3, 0x50, + 0xF2, 0x16, 0x98, 0xEB, 0x78, 0xB2, 0x9A, 0xDB, 0xD0, 0x71, 0x53, 0x58, 0xF9, 0x65, 0x27, 0x8A, 0xF8, 0x67, 0xC1, 0x2E, 0x2B, 0xB1, 0x9F, 0xFA, 0x16, 0x50, 0x27, 0x69, 0xF4, 0xFB, 0xDB, 0x20, + 0x82, 0x2D, 0x1D, 0xE1, 0xFB, 0x6E, 0x41, 0x6D, 0x82, 0x29, 0x32, 0xB5, 0xCD, 0x5B, 0x37, 0x0A, 0x58, 0x65, 0x56, 0x07, 0x56, 0xD7, 0x6D, 0x8C, 0x2F, 0xE4, 0x70, 0x4E, 0x0B, 0x15, 0x83, 0xEB, + 0x5D, 0x23, 0x5E, 0xC3, 0xFE, 0x7F, 0xF4, 0x98, 0xE1, 0x35, 0x61, 0x00, 0xC5, 0x80, 0x76, 0x3E, 0xB5, 0xF2, 0x36, 0x35, 0x62, 0x0C, 0xF6, 0xCC, 0x56, 0xE7, 0x4B, 0x48, 0x22, 0x3C, 0x70, 0xB5, + 0xE5, 0x23, 0xAC, 0x61, 0xEA, 0xAE, 0xF8, 0x8E, 0x4D, 0xD1, 0x50, 0x5D, 0x25, 0xC9, 0x65, 0x8B, 0x96, 0xE9, 0x32, 0xCE, 0x0B, 0xD0, 0xEF, 0xFE, 0x80, 0xBA, 0xA5, 0xD1, 0x05, 0xA6, 0x51, 0x4B, + 0x25, 0x57, 0x8D, 0x1F, 0x3F, 0xCC, 0x8F, 0xF5, 0xF9, 0x3A, 0x7C, 0xDD, 0xCC, 0xE0, 0x84, 0x0F, 0x63, 0x1B, 0xE0, 0x2B, 0xCA, 0x85, 0x20, 0x98, 0xDC, 0xFA, 0x06, 0x56, 0xF0, 0x8A, 0xF1, 0xBD, + 0xC8, 0xE2, 0x4A, 0x27, 0x46, 0x74, 0x16, 0xF4, 0x87, 0xAD, 0x02, 0x60, 0x22, 0xDD, 0x5E, 0x1E, 0x1E, 0xFD, 0xC9, 0xC2, 0xB4, 0x71, 0xE3, 0x26, 0x53, 0x65, 0xF2, 0x0B, 0xC8, 0x21, 0x86, 0x37, + 0x66, 0x25, 0x5D, 0x0A, 0xAC, 0x67, 0xB6, 0x58, 0xE6, 0x63, 0x3F, 0xD2, 0xC9, 0x3F, 0x80, 0xE5, 0x55, 0x5C, 0x6B, 0x3F, 0x9B, 0x9C, 0x54, 0x02, 0x62, 0xF9, 0x2E, 0x57, 0x5E, 0xCA, 0x8C, 0xBD, + 0xDE, 0xA2, 0x5E, 0x35, 0x59, 0x9F, 0xAF, 0xE0, 0x90, 0x20, 0x1D, 0x53, 0x1A, 0x96, 0xA6, 0x59, 0x5F, 0x6B, 0xC0, 0xA0, 0x83, 0x47, 0xF4, 0x54, 0xFC, 0x12, 0x6A, 0x16, 0x21, 0x64, 0xA0, 0xD5, + 0x07, 0x39, 0xF3, 0x0A, 0xB2, 0x29, 0x89, 0xF8, 0x88, 0xE4, 0xDF, 0xA3, 0x56, 0x13, 0x7A, 0x3E, 0x65, 0xEC, 0xB5, 0xF4, 0x7E, 0x20, 0x0E, 0x73, 0x36, 0xA2, 0xF0, 0xA5, 0xC5, 0x47, 0xA2, 0x36, + 0x7F, 0x1D, 0x0F, 0xDE, 0xA8, 0x9D, 0x00, 0x69, 0x8D, 0x96, 0x2E, 0x62, 0xE8, 0xDA, 0xA5, 0x70, 0xEE, 0x07, 0x7B, 0x9E, 0xB8, 0x18, 0xED, 0x82, 0x75, 0xB2, 0x3E, 0x73, 0x39, 0xFA, 0x3A, 0x6C, + 0x9E, 0xF0, 0xD3, 0xC9, 0x78, 0xEE, 0xF7, 0x5B, 0xC9, 0x77, 0xAA, 0xFE, 0x87, 0xB1, 0xA4, 0x1F, 0xED, 0x4C, 0x7D, 0xA1, 0x7E, 0x2B, 0xBE, 0xCC, 0xA8, 0xF4, 0x06, 0xF0, 0x40, 0xB1, 0x6F, 0xDD, + 0xFB, 0x2E, 0x8F, 0x47, 0x0C, 0x25, 0x40, 0x9B, 0x8C, 0x7C, 0x13, 0x88, 0xE6, 0x08, 0xEB, 0xBA, 0xE2, 0x67, 0xF7, 0x7C, 0x5F, 0xE0, 0x10, 0xF6, 0x91, 0x7B, 0xC6, 0xCA, 0x7B, 0xF6, 0x86, 0x5F, + 0xAA, 0x73, 0xE1, 0x0F, 0x2F, 0x60, 0xD2, 0x2D, 0xB2, 0x4A, 0x21, 0x71, 0x81, 0xBE, 0x56, 0xFD, 0x47, 0x3E, 0xE7, 0xAF, 0x5E, 0xD5, 0x60, 0x9A, 0xDA, 0x02, 0x36, 0xFA, 0xB3, 0x06, 0x6C, 0x3D, + 0xAD, 0x28, 0xA2, 0x4F, 0x67, 0xD4, 0xCC, 0x1C, 0xEF, 0xE6, 0x10, 0x6F, 0x5E, 0x54, 0x27, 0xAC, 0xCD, 0xC7, 0x3F, 0xF8, 0x85, 0x76, 0xA2, 0x7A, 0xEB, 0xE7, 0x1A, 0x33, 0xDB, 0x3C, 0x08, 0x02, + 0xD6, 0x97, 0x18, 0x95, 0x6C, 0xD9, 0xD1, 0x5A, 0xAA, 0x9A, 0x2D, 0xE3, 0xAC, 0x62, 0x10, 0x10, 0x0A, 0x2E, 0x39, 0xAF, 0x5B, 0xA9, 0x1D, 0xFA, 0x21, 0x8C, 0x53, 0x72, 0x66, 0x06, 0x2E, 0x32, + 0x6E, 0x2F, 0xF8, 0xC4, 0x4D, 0x17, 0x80, 0xFB, 0xAF, 0xF4, 0xAD, 0xBA, 0x82, 0x71, 0x17, 0xE0, 0xBC, 0xB7, 0xA4, 0xC8, 0xF2, 0x61, 0x39, 0x81, 0x71, 0x3F, 0xA5, 0x98, 0xA4, 0x68, 0x3A, 0x46, + 0x70, 0x85, 0x4C, 0x94, 0x67, 0xF2, 0x5A, 0x65, 0x6D, 0xDB, 0x6E, 0x7C, 0x3E, 0xF1, 0x92, 0xEB, 0xBD, 0xEE, 0x15, 0x3A, 0x59, 0x41, 0x61, 0x95, 0x26, 0xB3, 0x17, 0x87, 0x54, 0x4F, 0xE2, 0x31, + 0x2A, 0x28, 0x98, 0x9C, 0x6A, 0xA3, 0xAC, 0xC0, 0xFE, 0x44, 0x23, 0x14, 0xFD, 0xFB, 0xD8, 0x08, 0x7F, 0x2B, 0x75, 0x5E, 0xB4, 0xB7, 0x35, 0x55, 0x76, 0x28, 0x3F, 0xA8, 0x6C, 0xD2, 0xD9, 0xEC, + 0x1A, 0x6B, 0xD9, 0x4E, 0x6C, 0x5D, 0x72, 0x82, 0x02, 0xEC, 0x0B, 0x6E, 0xDF, 0xE1, 0xF3, 0x35, 0x84, 0x11, 0xC4, 0x9E, 0xC1, 0x10, 0x63, 0xAC, 0x1E, 0xDE, 0xB2, 0x1B, 0x95, 0xD7, 0x13, 0xD9, + 0x0B, 0xE4, 0x96, 0xD8, 0x55, 0x84, 0xAA, 0x64, 0x25, 0x47, 0x14, 0x80, 0x84, 0x4E, 0x5B, 0xE2, 0xD7, 0x05, 0x3E, 0x87, 0x22, 0x03, 0x64, 0x79, 0xBD, 0xCB, 0x36, 0x38, 0x35, 0xBB, 0x08, 0xB0, + 0x10, 0xDD, 0x0C, 0x08, 0x0E, 0x3D, 0x85, 0x24, 0xAE, 0x62, 0x21, 0x3E, 0x20, 0x8E, 0xC4, 0x12, 0xD0, 0x1F, 0xC9, 0xCE, 0xFA, 0x9C, 0x0A, 0xBD, 0x39, 0x64, 0x96, 0x45, 0x51, 0x84, 0xDB, 0x24, + 0x4A, 0xD6, 0xBE, 0xB4, 0x5F, 0xB7, 0x68, 0x47, 0x91, 0x62, 0x47, 0x44, 0x33, 0x52, 0x0C, 0xE0, 0x63, 0x03, 0xFF, 0xC6, 0x06, 0x07, 0xDD, 0x43, 0x29, 0x62, 0x88, 0x4F, 0x8A, 0xA6, 0x54, 0x39, + 0x98, 0xE1, 0xFB, 0x24, 0xDA, 0xF8, 0xAB, 0x3F, 0xF8, 0x62, 0xA8, 0x16, 0xA3, 0x98, 0x28, 0xF5, 0x7B, 0x54, 0x7A, 0xE7, 0x66, 0x98, 0x3F, 0x7C, 0xFA, 0xC8, 0x50, 0x23, 0xDC, 0x65, 0x53, 0x43, + 0x12, 0x74, 0xB8, 0x40, 0x19, 0xDB, 0xD8, 0x5D, 0x2C, 0x42, 0x9D, 0x2B, 0x01, 0xE3, 0xC0, 0xA5, 0xDE, 0x1E, 0x6C, 0xC8, 0x5E, 0x62, 0x57, 0x9B, 0x00, 0x12, 0x6E, 0x6F, 0xE8, 0x1A, 0xB2, 0xEC, + 0x08, 0x85, 0xD4, 0x30, 0x98, 0xA6, 0xF2, 0x15, 0x94, 0xD6, 0x67, 0x0F, 0x3E, 0xAB, 0x54, 0xEF, 0x3E, 0x30, 0xC7, 0x38, 0x96, 0x46, 0x1F, 0xE3, 0xCA, 0x4E, 0x8E, 0xD9, 0x29, 0x3E, 0x4F, 0x27, + 0x6E, 0x18, 0xAA, 0xC8, 0x54, 0x46, 0xC0, 0xC2, 0x34, 0xFF, 0x6F, 0x9A, 0xE1, 0x1A, 0x09, 0x89, 0x9B, 0x3D, 0x22, 0x1C, 0xC6, 0xC4, 0xB3, 0x63, 0xF7, 0xBE, 0x27, 0xAD, 0xF3, 0xF5, 0x1C, 0xE4, + 0xBD, 0x8F, 0x51, 0xC2, 0x1C, 0x7F, 0x44, 0xE3, 0x08, 0x3C, 0x8D, 0x04, 0x71, 0x24, 0x08, 0x4C, 0x1E, 0xDB, 0x09, 0x0A, 0x7D, 0x80, 0x56, 0x51, 0x7B, 0xBB, 0xD1, 0xF1, 0x87, 0xC4, 0x27, 0xDD, + 0xA5, 0x9E, 0x54, 0x5E, 0x8C, 0x60, 0x03, 0xCA, 0x0B, 0xC5, 0xBD, 0x38, 0x9E, 0xBD, 0x90, 0xB9, 0x97, 0x08, 0xC3, 0xD3, 0xC7, 0x40, 0x44, 0xEB, 0x2A, 0xB3, 0xCA, 0x6F, 0x72, 0xD4, 0xB2, 0xD4, + 0x91, 0x02, 0xB9, 0x74, 0x89, 0x64, 0x56, 0xFC, 0x67, 0x38, 0xE9, 0x0B, 0x94, 0x8C, 0x62, 0xE0, 0x16, 0x17, 0x14, 0x87, 0x1F, 0x57, 0x41, 0x9E, 0xCB, 0xAA, 0x16, 0xD0, 0x16, 0x65, 0xAC, 0xEB, + 0x39, 0x69, 0xB4, 0x84, 0xA2, 0xE0, 0x29, 0xED, 0x6A, 0x73, 0x30, 0x0E, 0x06, 0xC8, 0x50, 0xAF, 0xEF, 0xFC, 0x08, 0xCE, 0x29, 0x61, 0x85, 0x4E, 0x9A, 0xA0, 0x65, 0x38, 0xFF, 0x6D, 0x9F, 0x5A, + 0xEE, 0xAF, 0x57, 0x76, 0x1C, 0xB6, 0xAE, 0x36, 0x87, 0x1D, 0xC4, 0x17, 0x33, 0x2F, 0x30, 0x63, 0xBF, 0x91, 0x37, 0x21, 0x22, 0x68, 0xC3, 0x1F, 0x27, 0x8D, 0xC6, 0x85, 0xC1, 0xAD, 0x44, 0xD2, + 0x22, 0x56, 0x6F, 0x9F, 0x18, 0x82, 0x3D, 0x55, 0x0E, 0x89, 0x86, 0x51, 0xD7, 0x65, 0x57, 0x1A, 0x10, 0x69, 0xB8, 0x27, 0x48, 0x61, 0x85, 0x34, 0x59, 0xCF, 0x49, 0xDB, 0x92, 0x37, 0x44, 0xC9, + 0xC5, 0xC9, 0x3D, 0xD2, 0x6F, 0x66, 0x3F, 0x9A, 0xDD, 0xD0, 0xBF, 0x56, 0x38, 0x05, 0xB4, 0xB7, 0x47, 0xC0, 0xA6, 0xE5, 0xB5, 0x86, 0x90, 0x0C, 0x57, 0x25, 0x96, 0xF2, 0x12, 0x01, 0xD3, 0x74, + 0x55, 0x53, 0xCA, 0x09, 0xD2, 0x19, 0xCB, 0x01, 0x79, 0xF0, 0xB1, 0x00, 0x17, 0xF0, 0xF1, 0x4D, 0x5A, 0xF3, 0xB9, 0x4B, 0xB4, 0xA9, 0x38, 0x61, 0x78, 0xA8, 0x2D, 0x2B, 0x14, 0x11, 0xED, 0x8B, + 0x95, 0xAC, 0x40, 0xAE, 0x73, 0xB2, 0x36, 0xD9, 0xB7, 0x83, 0x25, 0x0F, 0x1B, 0x9B, 0xBD, 0xBD, 0x88, 0xC0, 0x9E, 0xEB, 0x29, 0x0A, 0x83, 0xD8, 0x0A, 0x44, 0x47, 0x60, 0xB9, 0x83, 0xB2, 0x70, + 0x20, 0xF1, 0x28, 0xED, 0x00, 0xE5, 0xD1, 0xD3, 0xBB, 0xC8, 0xCE, 0x86, 0x21, 0x4E, 0xB5, 0xF5, 0x33, 0xCC, 0x80, 0xF2, 0x78, 0xB1, 0x92, 0xB5, 0x7A, 0xBB, 0x0F, 0xFA, 0x70, 0x3E, 0xBF, 0x0B, + 0xAA, 0xE4, 0x92, 0x6D, 0x63, 0xC0, 0xFF, 0x51, 0x8A, 0x9B, 0xBE, 0xB3, 0x48, 0xD5, 0xB5, 0xA0, 0x4F, 0x6F, 0xFF, 0xCF, 0xD3, 0xA4, 0x25, 0xE5, 0x08, 0xBD, 0xAB, 0x88, 0xB4, 0x05, 0x7D, 0x94, + 0xD6, 0xF8, 0xB1, 0xB0, 0x56, 0x78, 0x3F, 0xE4, 0x0B, 0xE6, 0xD6, 0xEF, 0xDF, 0x53, 0x1F, 0x52, 0x81, 0x15, 0xE2, 0xB3, 0x21, 0x11, 0xD2, 0xB7, 0xCE, 0x59, 0x90, 0x84, 0xE2, 0x0F, 0x9E, 0xAD, + 0x59, 0x5A, 0xC9, 0x15, 0xCB, 0xAB, 0x2A, 0x48, 0x6C, 0x98, 0x5F, 0xB5, 0x0F, 0x6E, 0x2F, 0x3E, 0x16, 0x02, 0xD8, 0xE8, 0xCF, 0xA7, 0x68, 0x5A, 0xAA, 0x30, 0x5C, 0x06, 0x0F, 0x11, 0xDB, 0x98, + 0x07, 0x40, 0xBB, 0xF4, 0xBD, 0xF4, 0xA7, 0x1A, 0x1C, 0x7E, 0x37, 0xC6, 0xC6, 0xE8, 0x91, 0x20, 0xAD, 0x91, 0x2C, 0x2F, 0x2A, 0xC0, 0x25, 0x0F, 0x0F, 0xCE, 0x82, 0x6C, 0x55, 0xB6, 0xFB, 0x0F, + 0x63, 0x8D, 0xC0, 0xC5, 0x5E, 0x32, 0x7E, 0x92, 0x2D, 0xC4, 0x53, 0x75, 0x18, 0x69, 0xCD, 0xAB, 0xBC, 0x95, 0xA3, 0xC3, 0x50, 0x36, 0x8A, 0xF7, 0xAB, 0x4C, 0x17, 0xB0, 0x1D, 0x8B, 0xC4, 0x77, + 0x74, 0xB9, 0x01, 0xA1, 0x8A, 0xDB, 0x86, 0x98, 0x10, 0x37, 0x67, 0x21, 0xDC, 0x23, 0x3D, 0x81, 0x1D, 0xF2, 0x20, 0x8C, 0x04, 0xDF, 0x9B, 0xEE, 0xB8, 0x28, 0xB0, 0x02, 0xEA, 0xA1, 0xF8, 0x64, + 0x09, 0x1C, 0x1C, 0xD0, 0x90, 0xEA, 0x6F, 0xAB, 0xCC, 0x0B, 0x06, 0x4E, 0xD2, 0x91, 0x6A, 0xA1, 0x0F, 0x14, 0x4E, 0xE4, 0x47, 0x0A, 0x75, 0xAB, 0x04, 0xF2, 0xCC, 0xA1, 0xD8, 0xAC, 0x42, 0x48, + 0x4D, 0xCE, 0x93, 0x46, 0x76, 0xE7, 0x4A, 0x2A, 0x9E, 0x19, 0xB0, 0x96, 0xF1, 0x08, 0x8E, 0xBD, 0x2F, 0xDE, 0x8D, 0x16, 0x78, 0x46, 0xAA, 0x33, 0xD1, 0x81, 0x31, 0x72, 0xE9, 0x2B, 0x13, 0xB6, + 0x70, 0x81, 0xC4, 0x4C, 0x35, 0xF2, 0x55, 0xBB, 0x23, 0x6D, 0x0C, 0xF2, 0x9A, 0x58, 0xD0, 0xCC, 0xDE, 0xC3, 0x70, 0xC8, 0x6F, 0x84, 0x0D, 0xC6, 0xF9, 0x7A, 0x74, 0xBF, 0xAA, 0xCE, 0xFA, 0xBA, + 0x55, 0x65, 0xD7, 0x73, 0x62, 0x3A, 0x24, 0x32, 0x92, 0xE6, 0xDC, 0x76, 0x57, 0x39, 0x23, 0xD5, 0x9A, 0xC4, 0x43, 0xDB, 0x86, 0xA3, 0x12, 0x9A, 0x54, 0x73, 0xB1, 0x19, 0x4D, 0x21, 0xA4, 0x61, + 0xF6, 0x11, 0x4F, 0xDE, 0xC3, 0xA6, 0xD3, 0x8F, 0x28, 0xB3, 0x9B, 0x87, 0xF2, 0xEA, 0x06, 0x86, 0x67, 0x40, 0x94, 0x6B, 0x0D, 0x09, 0x7A, 0xF4, 0xB2, 0xC0, 0x6D, 0x36, 0xE9, 0xFC, 0xD2, 0x40, + 0x48, 0x90, 0x8E, 0x38, 0xA6, 0xF7, 0x6E, 0xAB, 0xBC, 0x19, 0x76, 0x17, 0x92, 0x82, 0xEB, 0x0E, 0x51, 0xD0, 0xE8, 0x3B, 0xE5, 0xCD, 0x93, 0xE6, 0x14, 0xC1, 0x6B, 0xEC, 0x1E, 0xEC, 0xB9, 0xF1, + 0x81, 0x08, 0x61, 0x70, 0x47, 0x59, 0xD1, 0xA0, 0x78, 0x92, 0xBF, 0x52, 0xF5, 0x5F, 0x89, 0x39, 0xA4, 0xDC, 0x30, 0x88, 0xFA, 0x16, 0x65, 0xF1, 0x35, 0xBD, 0x04, 0x77, 0xD0, 0x2D, 0xCD, 0xE5, + 0x7E, 0x0C, 0x1C, 0x0F, 0xAC, 0x0F, 0xA7, 0x0A, 0x25, 0x6F, 0x9B, 0x9B, 0xEB, 0xC7, 0xEB, 0x33, 0xF6, 0x6D, 0xB4, 0xE7, 0x9D, 0xF4, 0xB0, 0x70, 0xD8, 0x31, 0x81, 0x56, 0xFD, 0x65, 0xE1, 0xB3, + 0x6D, 0x37, 0xAC, 0xF9, 0xB0, 0xAA, 0xF0, 0x7C, 0x60, 0x34, 0x37, 0xC4, 0xA3, 0xD2, 0xFA, 0x2D, 0xCE, 0x6B, 0xCF, 0xAF, 0x18, 0x3F, 0x92, 0x1C, 0x6E, 0xE3, 0xE8, 0x7B, 0xD1, 0x75, 0x05, 0x7B, + 0xC9, 0x97, 0xF9, 0x0D, 0x18, 0x59, 0xEF, 0x76, 0x01, 0xE6, 0x8D, 0x35, 0x84, 0x62, 0xAF, 0xE3, 0xBA, 0xD1, 0x92, 0x83, 0x60, 0xE1, 0xAA, 0xFC, 0xCC, 0x17, 0x0D, 0x0F, 0xD7, 0x65, 0x18, 0x0B, + 0x57, 0xB0, 0x33, 0xCF, 0xCC, 0xE2, 0x89, 0x87, 0x8F, 0x41, 0x9B, 0x7D, 0x44, 0x71, 0xB7, 0xB0, 0xF3, 0xBF, 0x42, 0x56, 0xC0, 0x68, 0xDB, 0xCD, 0xBA, 0x7B, 0x0F, 0x20, 0x2C, 0xC7, 0x52, 0x9A, + 0x76, 0xC0, 0x9D, 0xB1, 0x66, 0xA1, 0x98, 0x5E, 0x10, 0xB4, 0x6F, 0x83, 0x0F, 0x08, 0xF7, 0x3E, 0xB2, 0x54, 0xCC, 0x3E, 0x33, 0xD6, 0x90, 0xDF, 0xAB, 0xED, 0x3F, 0x77, 0xE4, 0xC4, 0x65, 0x47, + 0x39, 0x90, 0x9E, 0x86, 0x1D, 0x04, 0x87, 0x49, 0x35, 0xD1, 0x20, 0x5D, 0xF3, 0x94, 0x1B, 0x10, 0x3D, 0x60, 0xF7, 0x1C, 0x36, 0x2B, 0xF0, 0x21, 0x91, 0x93, 0xF9, 0xAD, 0xAE, 0x49, 0xD3, 0x06, + 0xF5, 0x0A, 0x34, 0x79, 0x09, 0x70, 0x8A, 0x41, 0x7C, 0x74, 0xF8, 0xB8, 0xC4, 0x4D, 0x8C, 0x7F, 0xBE, 0xD5, 0x2F, 0x1A, 0x00, 0x98, 0x88, 0xED, 0x7D, 0xA2, 0x55, 0x12, 0xD7, 0x3C, 0xA3, 0x76, + 0x02, 0xD4, 0x6E, 0xEC, 0x02, 0x9D, 0x4F, 0x16, 0x84, 0x91, 0xC7, 0x0F, 0x2D, 0x0F, 0x13, 0x58, 0xCE, 0x37, 0x0C, 0x2C, 0xF2, 0x82, 0x35, 0x00, 0xE9, 0x89, 0xFB, 0x24, 0x72, 0x3C, 0x21, 0xDD, + }, + .t1_len = 2304, + .t1 = { + 0x94, 0x06, 0xE4, 0xDC, 0xE8, 0x12, 0xBE, 0x92, 0xE1, 0x53, 0xE0, 0x75, 0x2C, 0xFE, 0x26, 0xC1, 0x12, 0x7E, 0x9C, 0x80, 0xC8, 0x11, 0x3E, 0x12, 0x16, 0x95, 0xF9, 0x01, 0x4E, 0x03, 0xFF, 0xF1, + 0xFD, 0x7B, 0xE3, 0xB0, 0xF4, 0x0E, 0xEE, 0x5B, 0x02, 0xF5, 0x60, 0x1E, 0x2F, 0xC3, 0xAF, 0xF0, 0xCD, 0xF7, 0xE7, 0xE7, 0x34, 0x99, 0x9C, 0x7F, 0xC4, 0xEB, 0x9D, 0xDA, 0x81, 0x8C, 0x52, 0x06, + 0x93, 0xFE, 0x38, 0xE4, 0x49, 0xBE, 0x4C, 0xCF, 0x03, 0xFE, 0xA1, 0x72, 0x8E, 0x4C, 0xCA, 0x64, 0xFD, 0x11, 0x0B, 0xFC, 0x8E, 0xC9, 0xCB, 0x79, 0x50, 0x3B, 0xD5, 0x53, 0xF5, 0x89, 0x9A, 0x2F, + 0x63, 0x16, 0x5D, 0x19, 0x32, 0x72, 0x7D, 0xB7, 0x44, 0x72, 0x65, 0xF7, 0x96, 0xF4, 0xFD, 0xBC, 0xFE, 0xA6, 0xF4, 0x05, 0x9E, 0x88, 0x34, 0x34, 0xC7, 0x98, 0xB8, 0x68, 0xF9, 0x86, 0x60, 0x5D, + 0x4D, 0x03, 0xD3, 0x04, 0xB6, 0x77, 0xE3, 0x0F, 0xF7, 0xD7, 0x83, 0x0A, 0xDD, 0x06, 0x65, 0x2B, 0xCC, 0x1B, 0xF0, 0x4D, 0x33, 0xDF, 0xFE, 0xFC, 0xEF, 0x63, 0x4A, 0xF5, 0xBA, 0xE0, 0xD5, 0xC6, + 0xBA, 0xB6, 0xC5, 0x64, 0xF1, 0x95, 0x20, 0x82, 0xAA, 0x38, 0x25, 0x53, 0x20, 0x01, 0x9C, 0xBC, 0x8E, 0xCA, 0x07, 0x3D, 0x80, 0xAF, 0x0A, 0x59, 0x6E, 0x4D, 0x33, 0xAD, 0x73, 0xB4, 0xF1, 0xED, + 0xD4, 0x20, 0xE0, 0x90, 0x0B, 0xED, 0x47, 0x49, 0x5A, 0x88, 0x62, 0xD4, 0xA9, 0xCD, 0xDE, 0xD0, 0xDE, 0xA7, 0x74, 0xCD, 0xE0, 0x23, 0x8C, 0x71, 0x2B, 0x8A, 0xA9, 0x82, 0x47, 0x56, 0x66, 0x0D, + 0x2B, 0x34, 0xE4, 0x7E, 0x4B, 0x59, 0x42, 0x5F, 0x17, 0xA9, 0x60, 0x8D, 0xAD, 0x38, 0x28, 0xEC, 0x9D, 0x8A, 0xDB, 0x5D, 0xD3, 0x8C, 0x7D, 0x53, 0xDD, 0xA6, 0xDA, 0xC7, 0x4D, 0x3F, 0xD0, 0x3C, + 0x00, 0xB5, 0x9E, 0xE9, 0xA0, 0xE5, 0x27, 0x6E, 0x3E, 0x75, 0xD0, 0x13, 0x61, 0x01, 0x66, 0x49, 0x1D, 0x87, 0x3A, 0x7D, 0xA2, 0xC9, 0xFD, 0xA3, 0x60, 0xA6, 0x47, 0x73, 0x25, 0x00, 0x58, 0x41, + 0x8F, 0xA7, 0x62, 0x63, 0x2D, 0xCB, 0x12, 0x63, 0x85, 0x27, 0x32, 0x60, 0x02, 0x18, 0x67, 0x53, 0xE6, 0xB5, 0xD3, 0x31, 0xE5, 0x64, 0x23, 0xC9, 0x70, 0x9D, 0x34, 0x9C, 0x69, 0x5A, 0x32, 0x8A, + 0x56, 0x2B, 0x13, 0x9A, 0xF5, 0x98, 0xF8, 0x5D, 0xCB, 0x35, 0x98, 0x40, 0x7D, 0x82, 0xF8, 0x49, 0xC2, 0x9A, 0x87, 0xDC, 0x41, 0xFA, 0xA7, 0x69, 0x8F, 0xAC, 0x7F, 0x20, 0x4D, 0x70, 0xD0, 0x7D, + 0x4A, 0xDC, 0x1D, 0x68, 0xFB, 0x46, 0x08, 0x63, 0xBB, 0x00, 0x2F, 0x3A, 0x23, 0x57, 0xCB, 0x65, 0xFB, 0x4B, 0x03, 0xBA, 0xB6, 0x8D, 0xB9, 0xB1, 0x1A, 0x09, 0xC9, 0x02, 0xE8, 0x12, 0x95, 0x91, + 0x54, 0x16, 0xB4, 0x51, 0xD8, 0xE5, 0xFB, 0xF7, 0x81, 0x33, 0xBE, 0xD2, 0x81, 0x81, 0x37, 0x17, 0xE3, 0x74, 0xC5, 0xB4, 0x15, 0xE7, 0x77, 0x3F, 0x95, 0xD8, 0x3D, 0x8B, 0xF9, 0x7D, 0x4A, 0xC4, + 0x5E, 0xAC, 0x28, 0x1E, 0x50, 0x89, 0x69, 0x32, 0xF7, 0xEE, 0xA4, 0x83, 0xE6, 0x98, 0xED, 0xD6, 0x07, 0xC3, 0xFF, 0xDD, 0xD3, 0x4C, 0x56, 0x67, 0x03, 0x28, 0xEB, 0xA5, 0xE1, 0xEB, 0x24, 0x9B, + 0x8E, 0x26, 0x85, 0x38, 0xBF, 0x4C, 0xF3, 0x43, 0x2E, 0xD5, 0xA9, 0x33, 0xB8, 0x2E, 0x6C, 0x0E, 0x96, 0x0D, 0xE1, 0x8A, 0x20, 0x9F, 0xA3, 0x90, 0x96, 0x93, 0x87, 0x88, 0x4D, 0xAD, 0x8D, 0x8E, + 0xE7, 0xE6, 0x0A, 0x89, 0x69, 0x90, 0x62, 0x16, 0x2F, 0x90, 0xBB, 0x28, 0xE4, 0xCC, 0xBA, 0x1A, 0x5F, 0x52, 0x6D, 0xE9, 0xCF, 0x7F, 0xEF, 0xEC, 0x7A, 0x77, 0xDD, 0xA0, 0x7C, 0xD7, 0x00, 0x09, + 0xE4, 0x8E, 0xBF, 0x8E, 0xDD, 0x9B, 0x34, 0x87, 0x26, 0xA9, 0x37, 0xE1, 0x4F, 0xF5, 0xEB, 0x6E, 0x79, 0xE3, 0xDB, 0x1B, 0x60, 0xD7, 0x0A, 0x73, 0x05, 0x11, 0x15, 0x4A, 0x8A, 0xB8, 0x75, 0xF8, + 0x6D, 0xEB, 0xCB, 0x9D, 0x79, 0x0F, 0xC4, 0x32, 0x84, 0x4E, 0x90, 0x3C, 0x8B, 0xD9, 0xFD, 0xB2, 0x8F, 0x99, 0x88, 0xDF, 0xAE, 0xA5, 0x56, 0xE9, 0x20, 0xE5, 0x79, 0x25, 0x47, 0xAE, 0xA7, 0xA4, + 0x5B, 0x4C, 0x7E, 0x68, 0x41, 0x61, 0x1E, 0x33, 0x06, 0x4E, 0x5C, 0xB5, 0x9B, 0xBA, 0xEC, 0xA6, 0x9E, 0x38, 0xA0, 0x99, 0x94, 0xAE, 0xEA, 0x3D, 0x10, 0xF6, 0xFC, 0x53, 0xF6, 0x43, 0x56, 0x2F, + 0xA0, 0x0A, 0x34, 0x12, 0xD4, 0xAF, 0xF8, 0x01, 0xD4, 0x8D, 0x0C, 0x58, 0xBA, 0x05, 0x5A, 0x42, 0xCD, 0xF6, 0xB8, 0xF1, 0x86, 0x16, 0x99, 0xEF, 0xD9, 0xAD, 0x9D, 0xF4, 0xCB, 0xB9, 0x88, 0xE7, + 0x22, 0x17, 0x12, 0xBB, 0x42, 0xA4, 0x3B, 0xE8, 0x32, 0x25, 0x09, 0x11, 0x1D, 0x3A, 0x8E, 0xBC, 0x97, 0xFA, 0xEB, 0xF9, 0xF8, 0x5D, 0x69, 0x20, 0x76, 0x5A, 0x18, 0x2A, 0xD9, 0xC4, 0x54, 0x27, + 0x99, 0x31, 0x70, 0x5E, 0xA2, 0x90, 0x3F, 0x6E, 0x18, 0x7D, 0x2A, 0xF6, 0xA5, 0xE4, 0xA8, 0x30, 0x54, 0x16, 0x8A, 0xA6, 0xA6, 0xF1, 0x27, 0xC8, 0xCE, 0x0C, 0x56, 0xA2, 0xEF, 0x67, 0xDC, 0x1C, + 0xD9, 0xB2, 0x2A, 0x51, 0x39, 0xDA, 0xC1, 0x92, 0xFF, 0xC5, 0x3A, 0x13, 0xEC, 0x52, 0xA3, 0x22, 0x07, 0xA9, 0x6A, 0x4F, 0xED, 0xB1, 0x20, 0x55, 0xFF, 0xDD, 0xBE, 0xE6, 0xAE, 0xF0, 0x72, 0xF7, + 0x5D, 0xB7, 0xC6, 0xCD, 0x37, 0xB2, 0x58, 0x9D, 0xC0, 0x0F, 0xBE, 0xF1, 0x33, 0x3E, 0xB1, 0x13, 0xC8, 0x22, 0x1B, 0xF8, 0x74, 0x0F, 0xD7, 0xBF, 0x7F, 0x39, 0xA5, 0x7E, 0x4A, 0xE2, 0xCE, 0x86, + 0xE0, 0xE8, 0xB4, 0xE9, 0x21, 0x4D, 0x67, 0x21, 0x46, 0xED, 0xE9, 0x85, 0x87, 0x15, 0x71, 0x56, 0x5E, 0x9F, 0x59, 0xCD, 0xA5, 0x92, 0x22, 0xAC, 0x9C, 0x6C, 0x00, 0xD5, 0xA7, 0xC9, 0xD8, 0xA3, + 0xE5, 0x46, 0xDE, 0xC8, 0x3C, 0x65, 0x54, 0xEA, 0x89, 0x13, 0x72, 0xBB, 0xCA, 0xE7, 0xD7, 0x76, 0x88, 0xDE, 0xD6, 0x0B, 0x52, 0x6C, 0x04, 0xC9, 0xBF, 0x0A, 0x7D, 0x96, 0x56, 0x81, 0x90, 0x4D, + 0xAC, 0x03, 0x79, 0x1F, 0x08, 0xB0, 0x71, 0xF0, 0xEE, 0x5B, 0xAB, 0xA1, 0xC4, 0x6B, 0x15, 0x61, 0x75, 0x6E, 0x58, 0x9C, 0x33, 0x7B, 0xAB, 0x4F, 0x2B, 0x75, 0xAE, 0x3B, 0xF6, 0xE7, 0x74, 0x3F, + 0x6C, 0xEE, 0x5F, 0x09, 0x93, 0xE7, 0x18, 0xC9, 0x58, 0x4D, 0x47, 0xEA, 0xD4, 0xC9, 0x61, 0xAE, 0x96, 0xF6, 0xD6, 0x02, 0xA5, 0x06, 0xA2, 0xA4, 0xC0, 0xF5, 0x7E, 0x88, 0x1D, 0x51, 0xDC, 0x24, + 0xF2, 0x77, 0xEB, 0xA9, 0xCC, 0x3C, 0x6F, 0x23, 0x58, 0x29, 0xB5, 0xBA, 0x87, 0xC2, 0x1F, 0x12, 0x32, 0x1C, 0xEE, 0x8B, 0x6E, 0xE9, 0x08, 0x9B, 0xB5, 0x2C, 0x3A, 0x71, 0xAD, 0x61, 0x12, 0x46, + 0xAE, 0xD9, 0x80, 0xC1, 0xB9, 0x47, 0xA6, 0x7C, 0x88, 0xA1, 0x10, 0xA7, 0xBD, 0x84, 0x49, 0xD0, 0x9C, 0xE3, 0x90, 0x6C, 0x65, 0x35, 0x45, 0x7D, 0x02, 0xF2, 0x32, 0x5C, 0x70, 0xEE, 0x78, 0x63, + 0xAE, 0x63, 0x23, 0x0F, 0xC2, 0x3D, 0xEC, 0xA2, 0x99, 0xBB, 0x5B, 0x0E, 0x4B, 0x1A, 0xE8, 0xE2, 0x40, 0x1D, 0xFB, 0x9D, 0x4B, 0xDD, 0xD0, 0x61, 0x18, 0xBD, 0x15, 0x0F, 0x4B, 0x5C, 0xD3, 0x85, + 0xAF, 0xB4, 0xFA, 0xD4, 0xEC, 0xA4, 0x6D, 0x61, 0xBE, 0xCA, 0xB1, 0x1D, 0x02, 0x70, 0x26, 0x67, 0x33, 0x33, 0xAB, 0x31, 0x4B, 0x9E, 0xF9, 0x1B, 0x7A, 0x7F, 0x94, 0x0B, 0xDA, 0x44, 0x44, 0xAE, + 0xFE, 0x37, 0x03, 0x6A, 0x43, 0xF2, 0xB6, 0x8D, 0x0D, 0xFF, 0xD7, 0xAF, 0x33, 0xA3, 0x63, 0x0F, 0xDB, 0x32, 0x5A, 0x74, 0xDA, 0x7B, 0x09, 0x0F, 0x94, 0x9D, 0x06, 0x4B, 0xF7, 0x45, 0xB8, 0x93, + 0x37, 0x15, 0x2B, 0x98, 0x0E, 0x4E, 0x20, 0xCC, 0x23, 0xFF, 0xAF, 0xCC, 0xBC, 0x7E, 0x95, 0x77, 0x04, 0xE9, 0x4B, 0xE7, 0xF3, 0xE8, 0x5F, 0x7F, 0xE8, 0x49, 0x6F, 0xD5, 0xAA, 0xB9, 0x67, 0xB2, + 0x7C, 0x3F, 0x17, 0x3E, 0x26, 0x26, 0x80, 0xD0, 0x44, 0x08, 0x85, 0xE6, 0xC0, 0xB2, 0xAA, 0xB0, 0x9A, 0xB8, 0x1F, 0x6D, 0xE5, 0xB2, 0x2D, 0x17, 0xD5, 0xA2, 0x11, 0x97, 0xD6, 0x98, 0x93, 0xBE, + 0xED, 0x51, 0x83, 0x4E, 0x2D, 0x7E, 0x3D, 0xAF, 0xF0, 0x4C, 0xF8, 0x4A, 0xA9, 0xC7, 0x79, 0x6E, 0xBB, 0x6A, 0xE2, 0x06, 0xC4, 0xE1, 0x66, 0x25, 0xFD, 0xFD, 0x61, 0x39, 0x85, 0x05, 0x48, 0x06, + 0x26, 0x7C, 0xD6, 0x9B, 0xFA, 0x8F, 0x5D, 0xD6, 0x0F, 0x4F, 0x21, 0x94, 0x12, 0xDF, 0x2B, 0xAB, 0xC9, 0x56, 0x41, 0xAE, 0x15, 0x54, 0x87, 0xFA, 0xF4, 0x13, 0x33, 0xF5, 0xE5, 0x1B, 0xEF, 0xC2, + 0xF9, 0x63, 0xE6, 0x2B, 0x74, 0x8B, 0x3D, 0x9C, 0x20, 0x20, 0x66, 0xD1, 0xEC, 0xBA, 0xB6, 0x03, 0x21, 0x79, 0x10, 0x58, 0x9B, 0xB9, 0x69, 0x55, 0x21, 0xA5, 0xC5, 0x2F, 0x12, 0x38, 0x2F, 0x0D, + 0xE3, 0x24, 0x3F, 0x9E, 0x92, 0xED, 0x60, 0x53, 0x12, 0x63, 0x7D, 0xCC, 0xE5, 0xAD, 0x80, 0x7D, 0xA0, 0xC9, 0x2E, 0x99, 0x32, 0x52, 0x05, 0x20, 0x41, 0xC7, 0xB6, 0x8F, 0x4E, 0xB1, 0xBB, 0xB7, + 0x08, 0x5A, 0x5B, 0x02, 0x04, 0x77, 0x98, 0x92, 0x30, 0xCB, 0xA8, 0x9F, 0x96, 0x6D, 0x34, 0x97, 0xC4, 0x04, 0x3D, 0x05, 0x6F, 0x79, 0x7E, 0xA0, 0xB4, 0x8E, 0x24, 0x7C, 0xAB, 0xBC, 0x7E, 0x59, + 0x73, 0x07, 0xDA, 0x60, 0x5A, 0x00, 0x81, 0x45, 0x45, 0x51, 0xC8, 0x96, 0xAB, 0x4E, 0xE1, 0x34, 0x6B, 0x90, 0x4E, 0x35, 0x8A, 0x58, 0xCA, 0x2F, 0x7B, 0x93, 0xDA, 0x32, 0x9D, 0x08, 0x0A, 0x49, + 0xDC, 0xF9, 0xD2, 0xC9, 0xD1, 0xBB, 0xD6, 0xBA, 0x82, 0x6C, 0xA7, 0x13, 0x3A, 0xB2, 0xDF, 0x61, 0xD7, 0x13, 0x16, 0xEB, 0xDD, 0xED, 0x88, 0x2E, 0x49, 0x83, 0xB7, 0x67, 0x46, 0xF7, 0x14, 0x36, + 0xD2, 0xD7, 0xC1, 0x4D, 0x94, 0x34, 0x71, 0x70, 0xEE, 0x00, 0x15, 0x54, 0x00, 0x28, 0x1B, 0xD3, 0xC6, 0xBF, 0xE5, 0xEC, 0xBF, 0x69, 0xDE, 0xA0, 0x59, 0x01, 0x63, 0xE3, 0xA2, 0x97, 0x10, 0xC4, + 0x10, 0x7A, 0x08, 0xD4, 0xDD, 0x30, 0xFD, 0x6E, 0x05, 0x0E, 0xA1, 0xE9, 0xE3, 0xF3, 0xBA, 0xCD, 0x74, 0x10, 0x35, 0xE3, 0x47, 0x18, 0xAF, 0xA9, 0xA9, 0xC8, 0xAB, 0x19, 0xEA, 0x9C, 0xD8, 0x75, + 0x11, 0xCC, 0x59, 0xCC, 0x60, 0x1B, 0xC6, 0x3B, 0x82, 0x0F, 0xD0, 0x96, 0x87, 0x1F, 0x95, 0x26, 0x34, 0xA2, 0xA3, 0x78, 0x87, 0x83, 0xAA, 0xE7, 0x6D, 0xA2, 0x05, 0xB1, 0xEB, 0x5E, 0x94, 0x42, + 0x16, 0x19, 0xFF, 0x47, 0x52, 0x5F, 0x05, 0x62, 0xE4, 0xA3, 0x63, 0x3A, 0xC7, 0xC4, 0x01, 0x7D, 0xA2, 0xC8, 0x13, 0x07, 0xBD, 0xBD, 0x74, 0xB2, 0xD9, 0x16, 0x1E, 0x99, 0xC1, 0x68, 0x6A, 0x9A, + 0xB1, 0xC9, 0x44, 0x1B, 0x0D, 0x35, 0xC1, 0xCE, 0x7E, 0x9A, 0x62, 0x88, 0x28, 0x92, 0x85, 0x02, 0x33, 0x20, 0x88, 0x9B, 0x63, 0x9E, 0xB9, 0xCD, 0x0A, 0x56, 0x92, 0x93, 0xE3, 0x67, 0xC2, 0xBD, + 0x1F, 0xEA, 0x68, 0x7F, 0x45, 0x1B, 0x3D, 0xA8, 0x80, 0x9A, 0x77, 0xCA, 0x31, 0x9D, 0xFC, 0xFF, 0xBA, 0xD4, 0x27, 0x24, 0xF2, 0xE0, 0x67, 0xCB, 0x3A, 0x85, 0xE7, 0x23, 0xCD, 0xD0, 0xEF, 0xC6, + 0xB4, 0xC9, 0x7B, 0x5A, 0x13, 0x6B, 0xBE, 0xFC, 0xB6, 0xF1, 0x34, 0x59, 0x2C, 0xED, 0xDD, 0x6A, 0xFC, 0x98, 0x30, 0x36, 0x5D, 0x75, 0xF7, 0x5A, 0x27, 0xCA, 0xC7, 0x22, 0x56, 0x07, 0x8E, 0xD0, + 0x20, 0xA4, 0x49, 0x30, 0xDE, 0x9C, 0x35, 0xCE, 0x96, 0xE1, 0x54, 0x4E, 0xE9, 0x85, 0x1B, 0xE6, 0x78, 0x48, 0x2A, 0x32, 0x7C, 0xFA, 0x37, 0xA9, 0x13, 0xE0, 0x45, 0xC8, 0xC2, 0x63, 0xD9, 0xB2, + 0x5E, 0xAE, 0x21, 0xA2, 0x66, 0x4A, 0xF9, 0x43, 0x03, 0x95, 0x16, 0x3F, 0x04, 0x56, 0xD1, 0xA5, 0x18, 0xF6, 0x09, 0x7C, 0x96, 0xDB, 0x8F, 0x50, 0x5F, 0x34, 0x40, 0xA6, 0xC8, 0xCC, 0x31, 0xB5, + 0x95, 0xAC, 0xFE, 0x9A, 0xA9, 0xCC, 0x1C, 0xCF, 0xF9, 0xFD, 0xA6, 0x56, 0xBC, 0xDB, 0x5E, 0xEB, 0x57, 0xF4, 0x1E, 0x94, 0x67, 0xC6, 0x43, 0xBA, 0x62, 0x79, 0xE5, 0x41, 0xE8, 0x6C, 0x91, 0x07, + 0x4E, 0x55, 0xC6, 0x3A, 0xDF, 0x41, 0x51, 0x7C, 0xEA, 0x5A, 0x6F, 0x62, 0x29, 0xF7, 0x10, 0x16, 0x62, 0xBB, 0x0A, 0xA0, 0xCE, 0xAB, 0x2B, 0x7F, 0x62, 0x11, 0x96, 0xC7, 0xA7, 0x7B, 0xB3, 0x27, + 0xC7, 0x68, 0xC4, 0x3D, 0x06, 0x9D, 0x71, 0xC3, 0x2C, 0x71, 0x2C, 0x83, 0x1D, 0x68, 0x50, 0xE6, 0xEB, 0x79, 0x3D, 0x7D, 0xEB, 0x08, 0xDE, 0x7A, 0x70, 0x4B, 0x38, 0x6D, 0xFD, 0x2B, 0x30, 0x72, + 0xC2, 0x6B, 0x89, 0xDF, 0x8D, 0x07, 0x2B, 0x3E, 0x9F, 0x56, 0x96, 0xA0, 0x73, 0x2E, 0x21, 0x5D, 0xF6, 0xDE, 0x47, 0x5D, 0x3A, 0x69, 0xF1, 0x11, 0x2F, 0x8B, 0x6B, 0x8E, 0xE7, 0x6B, 0x73, 0x9C, + 0x92, 0x76, 0xD9, 0xEE, 0x78, 0x17, 0xD9, 0x89, 0xAA, 0x07, 0x90, 0xD4, 0x6F, 0x8B, 0xE9, 0xBC, 0xF8, 0xA9, 0xDE, 0x83, 0xD3, 0xF3, 0xC3, 0x02, 0xA8, 0xAA, 0xBE, 0xE5, 0xC8, 0xFE, 0xBC, 0x2A, + 0xDC, 0x70, 0x6F, 0xC0, 0xEA, 0x55, 0xCD, 0x6F, 0x38, 0x37, 0x74, 0xF9, 0x55, 0xFE, 0xC7, 0x0A, 0x5F, 0x83, 0x80, 0x74, 0xDC, 0xB7, 0x31, 0x53, 0x2C, 0x94, 0x9C, 0x88, 0x84, 0xE9, 0x5F, 0xDE, + 0xCE, 0x3A, 0x7D, 0x9F, 0x7E, 0xA2, 0x1A, 0xC5, 0xA8, 0xAC, 0xDF, 0xAA, 0x89, 0x68, 0x1E, 0x95, 0x01, 0x4D, 0x5A, 0x23, 0x44, 0x31, 0x5B, 0xF8, 0xB3, 0xFF, 0x97, 0x12, 0xA0, 0x9A, 0x8F, 0xDE, + 0xB8, 0x29, 0x4C, 0x25, 0x7D, 0x16, 0xCC, 0xEF, 0xAA, 0x78, 0xDD, 0x0F, 0x5D, 0xFF, 0xE0, 0x49, 0xCE, 0x2B, 0x8A, 0xC7, 0xE1, 0x60, 0x02, 0xED, 0x1E, 0x32, 0x8C, 0x62, 0x86, 0xA1, 0x67, 0x4A, + 0x5C, 0x06, 0xF6, 0x28, 0x37, 0xAA, 0xF3, 0xEE, 0xFF, 0xFC, 0x11, 0x46, 0x94, 0x7A, 0x63, 0x0D, 0x82, 0x44, 0xAA, 0x72, 0x89, 0x8D, 0xFE, 0x5B, 0x94, 0x78, 0x63, 0x70, 0x64, 0x8A, 0x13, 0xF0, + 0xE1, 0x6D, 0x50, 0x27, 0x77, 0xEB, 0x8D, 0xF9, 0x62, 0xFC, 0x86, 0x3C, 0x77, 0xC1, 0x59, 0xBF, 0x64, 0xCC, 0x2A, 0x47, 0xCA, 0xF6, 0xB2, 0x12, 0xCB, 0xC6, 0x14, 0x2B, 0x5C, 0x9F, 0x5B, 0xFF, + 0xE2, 0xDD, 0x3B, 0xB1, 0xF8, 0x63, 0x23, 0x10, 0x74, 0x82, 0x96, 0xBB, 0x81, 0xB3, 0x62, 0xB7, 0xE4, 0x56, 0xEE, 0xE8, 0xDF, 0x29, 0x55, 0xFC, 0xDC, 0x04, 0xE5, 0x5D, 0x25, 0x16, 0xA8, 0x28, + 0x07, 0x12, 0xCA, 0x5B, 0x60, 0xEA, 0x90, 0x7D, 0x51, 0xB2, 0xFA, 0x72, 0xF9, 0xC7, 0x3D, 0xA7, 0xFE, 0x2C, 0x25, 0x98, 0x8F, 0x5B, 0xE1, 0xB8, 0x23, 0x68, 0x25, 0xC8, 0x3A, 0x02, 0x38, 0x22, + 0x39, 0x40, 0x2A, 0x29, 0x4E, 0xA4, 0xBE, 0x31, 0xA1, 0x7D, 0xBD, 0x31, 0xBA, 0x1B, 0xFF, 0xF8, 0x04, 0xCC, 0x78, 0x2F, 0xED, 0x78, 0x95, 0x09, 0x7F, 0x58, 0x3D, 0xD1, 0x3A, 0xCC, 0x85, 0x49, + 0x1B, 0xDD, 0x12, 0x3F, 0xE0, 0x2C, 0x14, 0x12, 0xE3, 0x42, 0x61, 0x7D, 0x9C, 0x26, 0xB8, 0xD9, 0x87, 0x7C, 0xAD, 0x5A, 0x72, 0xD2, 0x32, 0x80, 0xB5, 0x27, 0x61, 0x47, 0xA7, 0x25, 0x84, 0xDA, + 0xE6, 0x17, 0x23, 0x15, 0x8B, 0x9A, 0x54, 0x79, 0xD6, 0x6B, 0x6D, 0x8A, 0x6C, 0x4D, 0xB0, 0xF2, 0xE7, 0x1E, 0xDD, 0x46, 0x58, 0x85, 0xC3, 0x3A, 0x69, 0xA8, 0xA7, 0x4E, 0x78, 0x16, 0x08, 0xF0, + 0x64, 0x16, 0x86, 0x6D, 0x19, 0x6B, 0x69, 0x5E, 0x70, 0xA4, 0x3B, 0x7D, 0xEA, 0xBE, 0x8C, 0x00, 0x0D, 0x79, 0xEE, 0x16, 0x03, 0xD4, 0x7C, 0x45, 0xCC, 0xB8, 0x5B, 0xBF, 0x79, 0x2D, 0x59, 0x14, + 0x6F, 0xA3, 0x22, 0x86, 0x97, 0x6F, 0xF5, 0x91, 0x72, 0x62, 0x96, 0x38, 0xE1, 0xA0, 0x70, 0xCB, 0x0F, 0x0E, 0xCB, 0xF8, 0x09, 0xF9, 0xF5, 0xB8, 0x73, 0xFB, 0xEF, 0x96, 0x87, 0x4F, 0xCD, 0xED, + 0x58, 0xA2, 0xC0, 0xA4, 0x99, 0x06, 0xD9, 0x09, 0x1D, 0x29, 0xB2, 0x1D, 0x0A, 0x7B, 0x89, 0x94, 0x52, 0x5D, 0x08, 0x88, 0x74, 0x8F, 0xB7, 0xDE, 0xE1, 0x60, 0xF2, 0xFC, 0xC7, 0x89, 0x52, 0xBB, + 0x57, 0xBE, 0x4D, 0x36, 0x68, 0x5B, 0xE4, 0xF2, 0xB1, 0x45, 0xBC, 0xAC, 0x40, 0xE0, 0xDB, 0x30, 0x60, 0x87, 0x2D, 0x81, 0x76, 0x63, 0x91, 0xD4, 0xEC, 0x0B, 0x04, 0x60, 0x9F, 0x4F, 0x2D, 0xA2, + 0x28, 0x94, 0x15, 0x45, 0x8D, 0x5F, 0x15, 0x22, 0x3C, 0x8E, 0x91, 0x11, 0x88, 0xC7, 0x82, 0x5F, 0x52, 0xA0, 0xA3, 0xA2, 0xC2, 0xCA, 0x8B, 0x62, 0xA7, 0x4B, 0x03, 0x71, 0x59, 0xE5, 0x4D, 0x99, + 0x73, 0xC8, 0x00, 0x54, 0x3D, 0x2F, 0x6C, 0x4C, 0x0D, 0x9E, 0x3B, 0x09, 0x39, 0xC1, 0xC1, 0x68, 0x05, 0xE5, 0x79, 0x46, 0x95, 0x49, 0x9C, 0xE0, 0x13, 0xCF, 0xB9, 0xB0, 0xEA, 0xEE, 0xD8, 0xDD, + }, + .pkcs8_len = 0, + .spki_len = 0, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 4668, + .sig = { + 0x37, 0xBD, 0x0C, 0xCB, 0xC5, 0x4E, 0x5A, 0x48, 0x0F, 0x2F, 0xBB, 0x8E, 0xF3, 0x87, 0x9E, 0x83, 0x40, 0xD7, 0xF6, 0xC7, 0x42, 0x42, 0xAD, 0x44, 0xD3, 0xE8, 0xB0, 0x78, 0x3C, 0xC5, 0xBF, 0x21, + 0x36, 0xD7, 0xBD, 0x4A, 0x32, 0xA9, 0x55, 0x2F, 0xE0, 0xE8, 0xAF, 0x8E, 0x87, 0xD5, 0x41, 0x1D, 0x76, 0x8A, 0x69, 0x2F, 0xE2, 0xC5, 0x03, 0xA7, 0x0C, 0xCB, 0xC0, 0x3A, 0x34, 0xB3, 0xC1, 0xF0, + 0x81, 0x5B, 0x26, 0x4B, 0x57, 0x2A, 0x9E, 0x74, 0x60, 0x9B, 0x9A, 0xD7, 0x29, 0x3B, 0xE3, 0x72, 0x7B, 0xFE, 0x17, 0x58, 0x3B, 0x3B, 0x63, 0x4F, 0x0A, 0x11, 0x9D, 0x79, 0x3E, 0xB1, 0x4D, 0xFF, + 0x18, 0x64, 0x3D, 0x1C, 0x34, 0x6B, 0x65, 0xE5, 0x73, 0xEF, 0xB9, 0xD5, 0x3B, 0xFA, 0x4C, 0x20, 0x05, 0x5D, 0x55, 0xF7, 0x54, 0xAF, 0x2F, 0x73, 0xFC, 0x38, 0x62, 0x67, 0xD5, 0x89, 0x0B, 0x39, + 0x13, 0x01, 0x41, 0x55, 0x93, 0xB2, 0xC5, 0x69, 0x5B, 0x9C, 0x06, 0xF0, 0x01, 0xF8, 0x84, 0x5C, 0x7C, 0xFA, 0xD7, 0x7C, 0x04, 0xE4, 0x11, 0x65, 0x18, 0xDF, 0x80, 0xF0, 0x41, 0xA5, 0x8A, 0x85, + 0x74, 0x48, 0xE7, 0x68, 0xA7, 0x1A, 0x7A, 0x01, 0xF2, 0x43, 0x31, 0x70, 0xB3, 0x71, 0xE8, 0xE3, 0x01, 0xA5, 0x37, 0x87, 0xD5, 0xEC, 0x77, 0x05, 0xA5, 0xEE, 0x1F, 0xE4, 0xFC, 0x04, 0x91, 0xCD, + 0xC6, 0xC8, 0x76, 0x96, 0x8A, 0x60, 0x6E, 0xC1, 0x38, 0x6F, 0x45, 0x1C, 0xE8, 0x54, 0x77, 0x34, 0x8D, 0xE1, 0xC6, 0x8E, 0xCC, 0x33, 0x95, 0x41, 0x61, 0x24, 0x90, 0xB2, 0x4C, 0x24, 0x2D, 0x25, + 0x87, 0x39, 0x81, 0xF9, 0xDE, 0xA6, 0x6D, 0x13, 0xF3, 0xC2, 0x10, 0x93, 0xEA, 0x48, 0x11, 0x51, 0xD1, 0x76, 0xA5, 0x50, 0x08, 0x42, 0x55, 0x0C, 0x26, 0xD0, 0xAF, 0xB1, 0xC6, 0xAE, 0xBE, 0x8E, + 0x42, 0x67, 0xE3, 0x6F, 0xD5, 0x70, 0x1E, 0x45, 0xD1, 0xDF, 0x15, 0x95, 0x9C, 0x7D, 0xC4, 0x4E, 0x7F, 0x5B, 0x6B, 0xA8, 0xCA, 0x04, 0xED, 0xF1, 0xE3, 0xE6, 0x48, 0x69, 0xFA, 0x15, 0x3B, 0xA7, + 0x46, 0x7F, 0x0D, 0x7B, 0x2F, 0xDC, 0x91, 0x24, 0x3A, 0x22, 0x39, 0x06, 0xF1, 0xAE, 0xA0, 0xD9, 0xFC, 0x14, 0x0F, 0x70, 0xCD, 0x02, 0x5A, 0x31, 0xB4, 0x0F, 0x22, 0xC4, 0x71, 0xBD, 0xD2, 0x36, + 0x5E, 0xD6, 0x30, 0x2D, 0x14, 0x81, 0x31, 0x6E, 0xE3, 0xC4, 0xC1, 0x70, 0xA1, 0x62, 0xEF, 0xE9, 0xFF, 0x41, 0x85, 0xE4, 0x50, 0x08, 0xF0, 0x7F, 0x6B, 0xDB, 0xAC, 0x22, 0x1D, 0xEC, 0x0B, 0xF0, + 0xAF, 0x88, 0x4B, 0x16, 0xC9, 0x5F, 0x34, 0x35, 0x01, 0xAA, 0x09, 0x8A, 0xD4, 0xA1, 0xF8, 0x20, 0x68, 0xFA, 0x1F, 0xBF, 0xF0, 0xE0, 0x40, 0x94, 0x6D, 0xCD, 0x50, 0xBF, 0x00, 0x9D, 0xF1, 0xFC, + 0xA4, 0xA3, 0xAA, 0xDB, 0x1C, 0x29, 0x51, 0xC0, 0x86, 0xD2, 0x7F, 0x20, 0x02, 0xDF, 0xD8, 0x54, 0xE5, 0x98, 0x52, 0xF4, 0x15, 0x30, 0x90, 0xDD, 0xC1, 0xA2, 0x1A, 0x6E, 0x0B, 0xE5, 0x92, 0x18, + 0x7A, 0x68, 0xAE, 0x08, 0x5B, 0x1D, 0x5D, 0x98, 0xBE, 0x8F, 0xCE, 0x5E, 0x24, 0x03, 0x1F, 0x47, 0xF8, 0x34, 0x30, 0x6B, 0xE5, 0xA5, 0xB6, 0x80, 0xAC, 0xFC, 0xD9, 0xF4, 0x04, 0xC1, 0xDE, 0x85, + 0x79, 0x66, 0xD2, 0x54, 0x6E, 0x66, 0x94, 0x01, 0x5F, 0x05, 0x02, 0xD0, 0xE6, 0x56, 0x8C, 0x9A, 0xA1, 0xB1, 0x3B, 0x3D, 0x7B, 0x61, 0xEE, 0x6A, 0x3D, 0xA0, 0x16, 0xDD, 0x34, 0xD6, 0x44, 0xB1, + 0x29, 0x7E, 0x63, 0x8D, 0xF0, 0xFC, 0xB6, 0xF6, 0x85, 0x57, 0x7E, 0x16, 0x4F, 0x5D, 0x6A, 0xA6, 0xF0, 0x70, 0xC1, 0xD0, 0x21, 0x55, 0x8C, 0xBC, 0xFD, 0x6F, 0x9B, 0xA3, 0x75, 0xE2, 0x89, 0x1F, + 0x67, 0x26, 0xCC, 0xE4, 0xCE, 0xBC, 0x89, 0xA9, 0x63, 0x57, 0x93, 0x0D, 0x04, 0x4C, 0x16, 0xAB, 0x29, 0x45, 0x30, 0x2C, 0xE0, 0xF2, 0xB6, 0x46, 0x17, 0x04, 0x6C, 0x3C, 0x1C, 0x4A, 0x6B, 0x34, + 0xD5, 0xAA, 0x07, 0x4E, 0x5F, 0xCB, 0x10, 0xBB, 0xA4, 0xC2, 0xA6, 0x08, 0x26, 0x5F, 0x45, 0xD7, 0x45, 0x10, 0x75, 0x0E, 0xAC, 0x67, 0x3A, 0x82, 0x8D, 0x5D, 0x30, 0x8F, 0x34, 0x07, 0x92, 0x31, + 0x33, 0xD5, 0x50, 0xB2, 0x57, 0x85, 0xA8, 0x39, 0x02, 0x42, 0xDC, 0x27, 0xB0, 0x82, 0xD3, 0x87, 0xAB, 0xCC, 0xDA, 0x7C, 0xD4, 0xD6, 0xEE, 0x5E, 0xAB, 0x8D, 0x51, 0xC8, 0x76, 0x9C, 0x24, 0x3A, + 0x95, 0x88, 0xF0, 0x45, 0xCC, 0xD9, 0xA5, 0x17, 0x2D, 0x99, 0xD0, 0x4E, 0xE4, 0x39, 0x59, 0xDC, 0x4D, 0x95, 0xBE, 0xAC, 0x06, 0x14, 0xA2, 0xF8, 0x50, 0x97, 0xED, 0x1C, 0x47, 0x61, 0x38, 0x42, + 0x9D, 0x12, 0xC7, 0x75, 0x8F, 0xA5, 0x28, 0x75, 0xC7, 0x38, 0xD4, 0x6E, 0xF2, 0xD9, 0x67, 0x51, 0x90, 0xFB, 0x72, 0x65, 0xF9, 0xAA, 0xC8, 0xC6, 0xF1, 0x73, 0xE8, 0xD5, 0x5C, 0x6B, 0x33, 0x81, + 0x9F, 0xBF, 0x9B, 0x5B, 0xD3, 0x12, 0x4D, 0x30, 0xC5, 0x81, 0x3E, 0x44, 0x7F, 0xAE, 0x23, 0xFC, 0xA5, 0xDB, 0x43, 0x8E, 0xC5, 0xCC, 0x8A, 0x66, 0xDE, 0xEB, 0xEB, 0x39, 0x53, 0x49, 0x29, 0xCE, + 0x4C, 0xE0, 0xB9, 0x8F, 0x1C, 0xA0, 0xE2, 0xC7, 0xD4, 0x53, 0x81, 0xC8, 0xF2, 0xE2, 0xFD, 0x2F, 0xED, 0x40, 0x6B, 0x29, 0xCC, 0x6A, 0x09, 0xD8, 0x1B, 0x44, 0xA4, 0x4F, 0x16, 0xC1, 0x50, 0xD8, + 0x65, 0xE8, 0xEA, 0x60, 0x60, 0xA8, 0x58, 0x39, 0x7C, 0x07, 0xF8, 0x57, 0x3A, 0x9C, 0xA2, 0x93, 0x00, 0x7D, 0x1B, 0xE4, 0xDD, 0xD8, 0xA5, 0x37, 0xDD, 0x9A, 0x57, 0x7F, 0x5E, 0x42, 0xF3, 0xEC, + 0xB4, 0x8F, 0x75, 0x81, 0x51, 0xA4, 0x01, 0xCA, 0xF2, 0x26, 0xA4, 0x8D, 0x94, 0x81, 0x9D, 0x2A, 0x43, 0xED, 0x08, 0xCD, 0xB6, 0xAE, 0xDD, 0x64, 0x01, 0x14, 0x03, 0x22, 0x31, 0x3B, 0xFD, 0xE2, + 0x76, 0x05, 0x71, 0x7E, 0x35, 0x66, 0xDD, 0x31, 0xBB, 0x5C, 0x52, 0x71, 0x45, 0x90, 0x45, 0x93, 0xA4, 0x74, 0x41, 0xD2, 0xF3, 0xC7, 0x44, 0x2C, 0x63, 0x69, 0x5D, 0xD0, 0xC3, 0x60, 0xBD, 0xA9, + 0x95, 0xFB, 0xFE, 0xC3, 0xE6, 0xC6, 0x63, 0xD1, 0xD2, 0x2D, 0x89, 0x0D, 0x7D, 0xF7, 0x05, 0x98, 0xF1, 0xBB, 0xC6, 0x19, 0x2A, 0x4F, 0x3A, 0x0A, 0x45, 0x8A, 0x95, 0x44, 0xCA, 0xDD, 0x6F, 0x18, + 0xDF, 0xA9, 0xEE, 0xA6, 0xE3, 0x20, 0x6B, 0xDE, 0x60, 0xED, 0x1C, 0x57, 0xCC, 0xC8, 0x00, 0x5F, 0x7C, 0x7C, 0x82, 0x74, 0xC1, 0x40, 0x7C, 0x8F, 0xAF, 0x4E, 0xBD, 0x69, 0xD5, 0x76, 0x19, 0x79, + 0xF9, 0x07, 0xCF, 0xD0, 0x62, 0x4E, 0xC7, 0xBA, 0x1F, 0xD7, 0xB5, 0x67, 0x81, 0xAC, 0x71, 0xA4, 0xA5, 0x26, 0x84, 0xFF, 0xC3, 0x2D, 0x5B, 0x53, 0x3C, 0xB5, 0x6C, 0x07, 0xF6, 0x35, 0xF5, 0x79, + 0x69, 0xC8, 0xF1, 0x58, 0x8D, 0x34, 0xD0, 0xE7, 0xA1, 0xC7, 0xA9, 0x42, 0xAA, 0xA3, 0xF3, 0x56, 0x0B, 0x0D, 0xB4, 0xF8, 0xCE, 0xBC, 0xAF, 0x6F, 0x25, 0x24, 0x11, 0x4A, 0x5F, 0x6A, 0xF7, 0x1B, + 0x5F, 0x50, 0xE9, 0x42, 0xE6, 0x74, 0xA8, 0x77, 0xC1, 0x74, 0xD9, 0x22, 0x00, 0x86, 0x5A, 0x5A, 0x06, 0xFB, 0x2D, 0x7F, 0xB4, 0x74, 0x41, 0x46, 0x75, 0xED, 0x31, 0x72, 0xF5, 0xF1, 0x53, 0x8F, + 0x58, 0x1E, 0xDE, 0x5E, 0xDD, 0x74, 0x5B, 0x55, 0xF9, 0xA2, 0xFC, 0x49, 0x95, 0xEB, 0x98, 0x4B, 0x8A, 0x12, 0xD6, 0xF6, 0x5A, 0xAE, 0xDF, 0x8D, 0x8D, 0x6F, 0xF5, 0x3C, 0xE2, 0x38, 0xC3, 0xA6, + 0x6C, 0xF2, 0x34, 0xF5, 0x94, 0x36, 0x47, 0x1C, 0x9F, 0xCB, 0xD3, 0x8E, 0x7F, 0x26, 0xBD, 0xF9, 0x74, 0x1B, 0x59, 0x9E, 0x16, 0xB8, 0xF7, 0xED, 0x46, 0x44, 0xBB, 0x6A, 0xBE, 0x81, 0xBB, 0x94, + 0x0C, 0x24, 0xFA, 0x62, 0x0F, 0x44, 0x35, 0x84, 0xF9, 0x9B, 0xB9, 0xDC, 0x25, 0x71, 0xB5, 0xEB, 0x81, 0x19, 0x27, 0x52, 0x9C, 0x7A, 0xDC, 0xEB, 0xEE, 0xF7, 0xAF, 0x05, 0xBA, 0x7E, 0x88, 0x89, + 0x9F, 0xAB, 0xF8, 0x74, 0x0F, 0xCD, 0xD1, 0x27, 0x5B, 0x12, 0xF7, 0x2A, 0x75, 0xC6, 0xD0, 0x00, 0x56, 0x5C, 0x5A, 0xC8, 0x8F, 0xB1, 0xFD, 0x99, 0x5B, 0x84, 0xED, 0x38, 0x4D, 0x5D, 0x6A, 0x60, + 0x29, 0x37, 0x37, 0xD7, 0x2C, 0xC1, 0x09, 0x44, 0x36, 0x39, 0x71, 0xDA, 0x44, 0xD5, 0xEA, 0xE9, 0xE8, 0xB1, 0xE8, 0x0D, 0x75, 0x76, 0xC5, 0x0A, 0xAF, 0xF6, 0x7E, 0x42, 0x31, 0x96, 0xF3, 0x78, + 0x57, 0xD1, 0xD2, 0x35, 0xAB, 0x28, 0x39, 0xAE, 0x37, 0x79, 0xF9, 0xF2, 0xF9, 0xB7, 0x59, 0xFC, 0x52, 0xDA, 0xAE, 0xB8, 0x63, 0x7B, 0x8F, 0x4F, 0xC9, 0x0B, 0xD9, 0x4A, 0xDB, 0x6F, 0x57, 0x72, + 0x20, 0x82, 0xE9, 0x43, 0xD7, 0xCE, 0x3E, 0x73, 0x50, 0x1D, 0x8C, 0x93, 0xB5, 0x21, 0x2D, 0xEC, 0xE4, 0x95, 0x35, 0x53, 0x6E, 0xFC, 0xEA, 0xB8, 0xB8, 0x5E, 0xB2, 0xAA, 0x94, 0xCB, 0xE7, 0x7B, + 0xAA, 0xDF, 0x46, 0x58, 0x92, 0x01, 0xA3, 0xA8, 0xAC, 0xA4, 0x83, 0x9E, 0x51, 0x9B, 0x6F, 0xD0, 0xCC, 0x52, 0xEA, 0x58, 0xA8, 0xAC, 0x08, 0xDC, 0x15, 0xEE, 0xF4, 0x8E, 0xDB, 0x89, 0xA1, 0xFC, + 0x46, 0xE7, 0x13, 0x53, 0xFE, 0x73, 0xF6, 0x8E, 0x0F, 0x48, 0x55, 0xB7, 0xFF, 0x73, 0x27, 0xAE, 0x4B, 0xCB, 0xA0, 0x9D, 0xE0, 0x33, 0x53, 0xD4, 0x1E, 0xDE, 0x26, 0x78, 0x5A, 0x94, 0x49, 0x6A, + 0xCB, 0x4E, 0x74, 0x3B, 0xA0, 0x65, 0xD1, 0x79, 0x3F, 0xBE, 0x5B, 0x29, 0x3A, 0x77, 0x1C, 0xCB, 0x8B, 0x8D, 0x8B, 0xD2, 0x76, 0x77, 0xD5, 0xFF, 0xF7, 0x43, 0xF9, 0x49, 0x77, 0x21, 0x9D, 0x55, + 0x57, 0x35, 0xE5, 0xD0, 0xAC, 0xE1, 0x18, 0xC2, 0x57, 0x1F, 0xC6, 0x96, 0xAF, 0x1F, 0xB0, 0xA1, 0x97, 0x6A, 0x37, 0x85, 0xB0, 0x89, 0x61, 0x11, 0x7F, 0x19, 0x98, 0xB7, 0xE6, 0x1C, 0xF8, 0x14, + 0xFE, 0x91, 0xA8, 0xB8, 0x1D, 0x62, 0xE4, 0x8D, 0x93, 0xB0, 0x28, 0x0D, 0xBA, 0xBF, 0x18, 0xE1, 0x12, 0x12, 0x43, 0xBF, 0xF3, 0x7B, 0x5A, 0xF7, 0x1E, 0x29, 0xA3, 0x1B, 0x48, 0x4A, 0xDA, 0x4F, + 0x1F, 0xBC, 0x88, 0x30, 0x11, 0x27, 0x76, 0x60, 0xAE, 0xB4, 0x71, 0xB3, 0x09, 0xFA, 0x00, 0x32, 0x23, 0x5B, 0x3B, 0x2E, 0x2B, 0x2C, 0xAF, 0xCC, 0xC5, 0x44, 0x61, 0xB0, 0xB4, 0x5A, 0xE1, 0x5D, + 0x92, 0xAD, 0x61, 0xB6, 0x4C, 0x5F, 0x37, 0x4A, 0x23, 0x74, 0x44, 0xF9, 0x63, 0x1D, 0xE4, 0x3C, 0x0B, 0x67, 0x8D, 0x03, 0xB6, 0x4E, 0xA3, 0xF9, 0x9B, 0xBB, 0xD1, 0x79, 0x61, 0x15, 0x39, 0xFC, + 0x91, 0x69, 0x3B, 0x81, 0xE6, 0xA2, 0xF2, 0xFC, 0x81, 0x70, 0xE8, 0xBF, 0xD6, 0xD5, 0xB7, 0x8A, 0x5C, 0xD6, 0x44, 0x88, 0x1A, 0x67, 0xFD, 0x28, 0xAC, 0xDA, 0x74, 0x70, 0x58, 0x47, 0x27, 0x6C, + 0x16, 0xBD, 0xF0, 0x9E, 0xBE, 0xBB, 0x21, 0x8C, 0xC6, 0x89, 0xB4, 0x50, 0x85, 0x43, 0xC3, 0x9E, 0xA6, 0x56, 0x44, 0xA7, 0xF3, 0x3D, 0xF4, 0x7D, 0x32, 0x72, 0xA3, 0x7C, 0xA8, 0x30, 0x76, 0x7B, + 0x23, 0xF5, 0x52, 0xA1, 0xB3, 0x89, 0xF1, 0x4B, 0xE8, 0x71, 0xFF, 0x72, 0x59, 0xFB, 0x3A, 0x32, 0x93, 0x0F, 0x56, 0xDD, 0x42, 0x71, 0xF0, 0x21, 0xAA, 0xAC, 0xD7, 0xA2, 0xAC, 0x82, 0x03, 0xCF, + 0x69, 0xE9, 0x64, 0x30, 0xA1, 0x6A, 0x2F, 0x96, 0xC1, 0x1F, 0xD2, 0xCD, 0x44, 0xE0, 0x86, 0xE1, 0x16, 0x8A, 0x8C, 0x1A, 0x63, 0x7E, 0x23, 0x21, 0xF6, 0x0C, 0xA5, 0x93, 0x0C, 0x02, 0xF9, 0x2D, + 0xFF, 0x2D, 0x30, 0xAB, 0x10, 0x5A, 0xF8, 0x46, 0xB1, 0x6A, 0x90, 0xE2, 0xA7, 0x4D, 0xBC, 0x97, 0xDA, 0x40, 0xA1, 0x3F, 0x40, 0x5B, 0x71, 0x04, 0xBF, 0x2F, 0x22, 0xFC, 0xA4, 0x2E, 0x3A, 0x50, + 0x0A, 0x72, 0x7A, 0xE1, 0xEA, 0x24, 0x01, 0x21, 0x60, 0x16, 0xFE, 0x8B, 0xF0, 0xDD, 0xBA, 0xE6, 0x8E, 0xD8, 0x74, 0x17, 0xFA, 0x76, 0x0D, 0xBA, 0x07, 0xD8, 0x4C, 0x26, 0x9C, 0xF4, 0x2B, 0xBE, + 0xB3, 0x7D, 0x5B, 0x90, 0xEB, 0x23, 0x69, 0x76, 0xB8, 0x6F, 0x4D, 0x8F, 0x35, 0xE7, 0x82, 0x83, 0x7E, 0x32, 0xA1, 0x95, 0xF9, 0xCF, 0xD6, 0xC6, 0x73, 0x53, 0x6A, 0xA0, 0x43, 0x5B, 0x38, 0x0C, + 0x02, 0xD1, 0xB7, 0xB0, 0xDE, 0x3C, 0x47, 0x9F, 0xE6, 0xB5, 0xFE, 0x6C, 0xF9, 0x7C, 0x3B, 0xD7, 0x46, 0x10, 0xCF, 0x15, 0x06, 0xE5, 0x99, 0x86, 0xF3, 0x81, 0x46, 0xB9, 0xA8, 0x96, 0x3C, 0xAE, + 0x08, 0x00, 0x30, 0x75, 0xFF, 0x60, 0x7D, 0x47, 0x0E, 0x87, 0xA7, 0x2E, 0x8F, 0xFB, 0xC7, 0xE1, 0x38, 0x38, 0xDA, 0x93, 0xDC, 0x3A, 0x4B, 0x3E, 0x52, 0x34, 0x75, 0xCD, 0xC4, 0xE4, 0x8C, 0x2A, + 0x54, 0x5F, 0x30, 0xE5, 0x89, 0x24, 0x7C, 0x64, 0x62, 0x2F, 0xA1, 0x05, 0x59, 0xB7, 0x24, 0xBB, 0x5F, 0xE8, 0x73, 0xED, 0xDF, 0x78, 0x38, 0xE1, 0x83, 0x2A, 0xD2, 0x17, 0xD4, 0xE8, 0x0B, 0x58, + 0xB9, 0xFB, 0x39, 0xB6, 0x6C, 0xBE, 0x9F, 0x26, 0x48, 0x09, 0xEE, 0xD5, 0x94, 0x23, 0xF0, 0xA3, 0xCD, 0x3F, 0x00, 0xAD, 0xFC, 0x47, 0x42, 0xCE, 0x1B, 0x3C, 0xB6, 0x5B, 0x2B, 0xD2, 0xE3, 0x10, + 0x59, 0x50, 0x9A, 0xFC, 0x7E, 0x48, 0x36, 0xDF, 0x0A, 0xE6, 0xF9, 0xD5, 0xC0, 0x63, 0x30, 0x95, 0x3F, 0xA2, 0xBB, 0x6F, 0xD0, 0x18, 0x7A, 0x6C, 0xAB, 0x88, 0x14, 0xEE, 0x12, 0xD1, 0x4E, 0xBC, + 0x6D, 0xEF, 0xFC, 0x23, 0xE1, 0xC9, 0x01, 0x65, 0xE2, 0xE7, 0x78, 0x59, 0x45, 0xF1, 0x8B, 0xCC, 0x74, 0xD8, 0xB1, 0xC6, 0xAF, 0xA1, 0x5B, 0x32, 0x6C, 0x04, 0x7D, 0x94, 0x66, 0x8C, 0x03, 0x32, + 0xD1, 0x47, 0xAF, 0x57, 0x52, 0x17, 0x64, 0x52, 0xC7, 0x12, 0x20, 0xB0, 0xA4, 0x32, 0xD4, 0x89, 0x9B, 0x6C, 0xEA, 0xA5, 0x87, 0x59, 0x9C, 0xAC, 0xF0, 0x04, 0xBA, 0x12, 0xA9, 0x0B, 0x26, 0x06, + 0x21, 0x43, 0x06, 0xFA, 0x30, 0x0A, 0x4A, 0x13, 0xBF, 0x8F, 0x99, 0x4F, 0x46, 0xF5, 0xDF, 0x92, 0xE6, 0xD3, 0xBF, 0x47, 0x2C, 0xF7, 0x29, 0xFF, 0xF6, 0x66, 0xF2, 0x07, 0xEA, 0x71, 0xD5, 0x2C, + 0xF6, 0xF2, 0xB1, 0x9C, 0x87, 0xCE, 0xAF, 0x08, 0xCD, 0x44, 0x5D, 0x18, 0x4F, 0x89, 0x81, 0xCA, 0x28, 0xCB, 0xFE, 0xA0, 0x03, 0x06, 0xAC, 0x76, 0x8B, 0x47, 0x15, 0x42, 0xF3, 0x27, 0x48, 0x76, + 0x68, 0x4B, 0xCE, 0x7C, 0x17, 0xEB, 0xEC, 0x6C, 0xC6, 0xD7, 0xF9, 0x0E, 0xC1, 0x3D, 0xA9, 0x4C, 0xD7, 0xB4, 0xE9, 0x8E, 0x1C, 0xFA, 0xBA, 0x8F, 0x9C, 0xDD, 0xBF, 0x08, 0xCF, 0xD7, 0xDD, 0x5E, + 0x3A, 0x73, 0x25, 0x66, 0x36, 0x65, 0x98, 0x0D, 0x3F, 0x55, 0x59, 0x22, 0x60, 0x8A, 0x05, 0xD9, 0xDC, 0x20, 0x76, 0x69, 0x29, 0x41, 0x30, 0x66, 0xB3, 0xB1, 0xAF, 0x98, 0x44, 0x31, 0x34, 0x5F, + 0xD0, 0x12, 0x1D, 0x16, 0x42, 0xEA, 0xB5, 0x84, 0xF7, 0x47, 0x37, 0x3D, 0x08, 0xCE, 0x5B, 0x2E, 0x26, 0xE7, 0x6B, 0x51, 0xAB, 0x58, 0xE3, 0x9E, 0x6F, 0x9E, 0x6C, 0x4C, 0x33, 0xF1, 0x52, 0xE5, + 0x03, 0x7F, 0x7F, 0x52, 0x76, 0x0A, 0x98, 0x36, 0x94, 0x1D, 0x43, 0xF4, 0x3C, 0x2E, 0x8C, 0x34, 0x6E, 0x40, 0x4A, 0xF3, 0x51, 0x80, 0x13, 0x3C, 0x2C, 0x8B, 0x44, 0x03, 0x86, 0x98, 0xFB, 0xE6, + 0xE8, 0x44, 0xEB, 0xC9, 0x66, 0x57, 0xD5, 0xD3, 0x24, 0xCE, 0xB2, 0xCC, 0x38, 0xA4, 0xF2, 0xE3, 0xB0, 0x09, 0x38, 0x39, 0x3B, 0x05, 0x4E, 0x19, 0xA1, 0xAF, 0x2C, 0x7E, 0x2C, 0xBB, 0xC1, 0xC4, + 0x52, 0xB6, 0x9D, 0x02, 0xA4, 0xBF, 0x04, 0xEB, 0x58, 0x42, 0xAA, 0x6A, 0x0A, 0xF8, 0xFB, 0x9D, 0x85, 0xD7, 0x98, 0x5B, 0x9B, 0xB2, 0x3D, 0x86, 0x06, 0x24, 0xB4, 0xE4, 0x04, 0x7E, 0x14, 0x26, + 0xF7, 0x17, 0x76, 0x7E, 0x51, 0x5C, 0x3D, 0x99, 0xF4, 0xF3, 0xA1, 0x05, 0x66, 0x56, 0x23, 0x2A, 0x21, 0x1C, 0xC2, 0xC8, 0x07, 0xF1, 0xF9, 0xF9, 0x61, 0x1D, 0xC8, 0xAE, 0x50, 0x81, 0x94, 0xF7, + 0xD6, 0x18, 0x2E, 0xE3, 0xAE, 0x96, 0x71, 0xB3, 0x45, 0xD0, 0x23, 0x18, 0x94, 0x78, 0x6E, 0x70, 0x72, 0x42, 0xF0, 0x68, 0x80, 0x69, 0x5A, 0x3F, 0xA6, 0x26, 0x89, 0x15, 0x74, 0xFA, 0xEE, 0xEE, + 0x83, 0x39, 0xDE, 0xBE, 0x23, 0x0E, 0xE7, 0x6B, 0x82, 0xA9, 0xAE, 0x4F, 0x03, 0xD9, 0xCC, 0xA2, 0x8F, 0x3B, 0x9F, 0x2F, 0x06, 0xAC, 0x23, 0xE3, 0xD2, 0xCF, 0x76, 0xF0, 0x19, 0x50, 0x6F, 0xEC, + 0x5C, 0x6E, 0x99, 0x07, 0x58, 0x7F, 0xB3, 0xBF, 0x4C, 0x2B, 0xE6, 0x58, 0xC5, 0x6E, 0xD6, 0x31, 0x88, 0x46, 0x56, 0xD6, 0xC2, 0x0E, 0xE1, 0x0B, 0x78, 0xD8, 0xF2, 0xD8, 0x01, 0x82, 0x30, 0xCD, + 0xF9, 0x5E, 0xB8, 0x6E, 0x9C, 0xFD, 0xA2, 0xE1, 0x55, 0xBA, 0x33, 0x58, 0x12, 0xFC, 0x72, 0xEB, 0x88, 0x0B, 0xEA, 0x3A, 0x8C, 0x3A, 0x98, 0xCB, 0x56, 0x71, 0xE0, 0xE4, 0x03, 0x70, 0x4A, 0x55, + 0x33, 0x62, 0x5B, 0x3E, 0xFA, 0x5C, 0xD3, 0x6C, 0x93, 0xDA, 0x37, 0x77, 0x21, 0xBF, 0x43, 0x82, 0xA0, 0xD0, 0x11, 0x77, 0xBC, 0xC5, 0xBC, 0xB4, 0xB7, 0x08, 0x23, 0x32, 0xE3, 0xE5, 0x85, 0x1B, + 0x17, 0xF7, 0xB9, 0xD9, 0x10, 0xD2, 0x19, 0xEC, 0x5F, 0x98, 0xB9, 0xCE, 0x2E, 0xD2, 0x7F, 0x40, 0xB5, 0x72, 0x13, 0x8F, 0xE9, 0xA0, 0x3F, 0x15, 0x48, 0x65, 0x23, 0xB2, 0x9A, 0xA4, 0xC6, 0x07, + 0x60, 0x17, 0xEF, 0xD2, 0x70, 0x70, 0x56, 0x0A, 0xC6, 0x13, 0xB3, 0x1D, 0x76, 0xB9, 0x60, 0x07, 0xEA, 0x98, 0xD7, 0xB0, 0x1D, 0x9A, 0x92, 0x54, 0x0C, 0x6A, 0x03, 0x0C, 0x4D, 0x0B, 0x98, 0x50, + 0x8A, 0x14, 0x51, 0xE6, 0x48, 0x7F, 0x11, 0x2E, 0xF9, 0xE9, 0x05, 0xBA, 0x88, 0x92, 0x7A, 0xD6, 0x19, 0xEE, 0xEC, 0x6B, 0x58, 0xEE, 0xF0, 0x62, 0xE9, 0x1D, 0x35, 0x10, 0xB4, 0xED, 0xDA, 0xB2, + 0xE5, 0xF9, 0x15, 0x46, 0x70, 0xEA, 0x8C, 0xF0, 0x00, 0x4C, 0xA4, 0xE2, 0xCC, 0xB5, 0xCE, 0x6C, 0x18, 0x70, 0xDA, 0x6B, 0xD8, 0xFD, 0xDC, 0x36, 0x41, 0x03, 0x91, 0x08, 0x82, 0x23, 0xF1, 0x53, + 0xF6, 0x83, 0x97, 0x6B, 0xAB, 0x00, 0x87, 0xB2, 0xAF, 0x15, 0x7C, 0xA7, 0x89, 0x3E, 0x5C, 0x34, 0xF8, 0x38, 0xB2, 0x2A, 0xE6, 0x51, 0x4A, 0xB3, 0x81, 0xF4, 0x7A, 0x63, 0x3E, 0xC8, 0x9A, 0x2E, + 0x1E, 0x51, 0x11, 0x18, 0x75, 0xB3, 0xAE, 0x9A, 0xEB, 0x66, 0x7D, 0xC8, 0x38, 0x6D, 0xB8, 0x1F, 0x13, 0xFF, 0x8D, 0xF7, 0x38, 0xB1, 0x02, 0x15, 0xDA, 0x52, 0x21, 0x01, 0xEF, 0xB8, 0xAD, 0xC9, + 0xB1, 0x08, 0x75, 0xA4, 0x79, 0xB6, 0x47, 0x93, 0xB2, 0x4C, 0x67, 0x68, 0x41, 0xE3, 0x5C, 0x97, 0xA8, 0xE7, 0xEE, 0xBC, 0x6C, 0x51, 0x72, 0xCA, 0x88, 0x66, 0x1F, 0x2B, 0x62, 0x86, 0x46, 0x31, + 0x2A, 0x68, 0x8C, 0xCC, 0x12, 0x43, 0x7D, 0x70, 0x39, 0x0C, 0x3E, 0x16, 0x21, 0x92, 0x0E, 0x65, 0x53, 0x98, 0xFF, 0x9A, 0x7E, 0x53, 0x74, 0xDF, 0xEC, 0xE4, 0x00, 0x19, 0x5B, 0x6A, 0x43, 0x1C, + 0xDC, 0xC4, 0xB2, 0xF4, 0x4D, 0xAA, 0xC9, 0xBF, 0x91, 0x5E, 0x1B, 0x23, 0xA8, 0x5F, 0xED, 0x35, 0xE3, 0xC4, 0x3F, 0xCF, 0x02, 0x13, 0x04, 0x02, 0x10, 0x94, 0x83, 0x13, 0x48, 0x98, 0x37, 0x08, + 0x0F, 0x1D, 0x80, 0x30, 0x27, 0xB0, 0x98, 0x95, 0x11, 0xD0, 0x63, 0x16, 0x7B, 0x36, 0x58, 0xD3, 0xF9, 0x8C, 0x0D, 0x2C, 0xA8, 0x79, 0x76, 0x53, 0x49, 0x28, 0x98, 0xC8, 0x14, 0x0E, 0x21, 0x86, + 0x9C, 0x56, 0x3A, 0x5C, 0x03, 0xB7, 0x86, 0x07, 0x8F, 0x63, 0x4D, 0x75, 0xED, 0x2B, 0xDA, 0xD2, 0x74, 0x22, 0x51, 0xB6, 0x36, 0x48, 0x7D, 0x1A, 0xFF, 0xAB, 0xF3, 0x1E, 0x66, 0x46, 0x98, 0xC1, + 0x77, 0x3F, 0x4E, 0x4D, 0xE9, 0xF2, 0xC3, 0xA4, 0xFE, 0xE7, 0x58, 0xEA, 0x07, 0x34, 0x89, 0x46, 0x99, 0x48, 0xBC, 0x9B, 0x50, 0xDB, 0x60, 0xD0, 0x5D, 0x9F, 0x18, 0x31, 0x41, 0x48, 0x94, 0xC2, + 0x06, 0x19, 0x0E, 0xCD, 0xE8, 0xF2, 0x49, 0xBD, 0x43, 0x57, 0x7C, 0x8D, 0x40, 0xCA, 0x61, 0x1D, 0x23, 0xB6, 0xF7, 0x54, 0xCB, 0x06, 0xC6, 0x77, 0xC7, 0x1A, 0x77, 0x00, 0xCB, 0x8A, 0xF9, 0x30, + 0xC5, 0xFF, 0xDB, 0x55, 0x4C, 0xA6, 0xAB, 0xE6, 0xD0, 0x83, 0xEE, 0x1A, 0x5A, 0xBF, 0xAA, 0x27, 0xA6, 0xF3, 0x1A, 0x83, 0x02, 0xBF, 0xD5, 0x78, 0xBC, 0x52, 0x93, 0xBD, 0xA4, 0xC1, 0x84, 0xE7, + 0xD7, 0xBB, 0x58, 0x9F, 0x6D, 0xEA, 0x11, 0xC9, 0xF3, 0x9A, 0xB9, 0xCD, 0x09, 0x8A, 0x72, 0x81, 0x63, 0xD7, 0x96, 0x2B, 0x6A, 0x40, 0x06, 0xF2, 0x65, 0x27, 0x73, 0xD5, 0xD8, 0xCA, 0xDA, 0x35, + 0xFB, 0x07, 0xDD, 0x8D, 0x39, 0x2D, 0xF7, 0x07, 0x9D, 0x1D, 0x72, 0x1D, 0xFA, 0xEC, 0xFF, 0xAC, 0xDB, 0x80, 0x81, 0x42, 0xFB, 0xA4, 0xF3, 0xC9, 0xB5, 0xC3, 0x1C, 0x81, 0xBB, 0x58, 0xA9, 0xAA, + 0x30, 0x1F, 0x3D, 0x54, 0xEB, 0x4B, 0x0D, 0xBF, 0xF7, 0xF2, 0x67, 0x73, 0xB4, 0x56, 0xD5, 0xC0, 0x2F, 0x94, 0x25, 0x4E, 0xB7, 0x7E, 0x35, 0x3A, 0x68, 0x75, 0x3D, 0xCD, 0xC6, 0x2E, 0xC2, 0x3B, + 0xDD, 0x5D, 0x6B, 0xBA, 0x07, 0xDB, 0x3E, 0xAC, 0x51, 0xE6, 0x4C, 0x34, 0xB4, 0xB5, 0x34, 0x38, 0xBF, 0x7C, 0x6E, 0xF9, 0xC6, 0x23, 0x7B, 0x68, 0xF6, 0x98, 0xE4, 0x31, 0x50, 0x77, 0x23, 0xA2, + 0xE3, 0xBC, 0x43, 0xDD, 0xB6, 0xD9, 0x52, 0xA4, 0xF1, 0x2B, 0x43, 0xF7, 0x64, 0xF7, 0x5B, 0x5C, 0x6C, 0xB8, 0x82, 0xF7, 0xFE, 0xB7, 0x38, 0xAE, 0x3F, 0xB9, 0x1C, 0xBF, 0x49, 0x7E, 0x8E, 0x1D, + 0x1B, 0x1D, 0x59, 0x22, 0x79, 0xAF, 0x26, 0x16, 0x6C, 0xCA, 0x5A, 0xBD, 0xD2, 0x8E, 0x6E, 0xFF, 0x4F, 0xBA, 0x74, 0x60, 0x5E, 0xA8, 0x85, 0xCE, 0xEB, 0x5A, 0x01, 0xEA, 0xFD, 0xE3, 0x16, 0x93, + 0x9C, 0x35, 0xB8, 0x01, 0x0D, 0xD8, 0x57, 0x9A, 0x3A, 0x94, 0xFC, 0x68, 0x5E, 0xEB, 0x1F, 0x62, 0x83, 0xC5, 0xE6, 0xAD, 0x51, 0xE8, 0x2A, 0x93, 0x51, 0xC9, 0xD1, 0xA3, 0xFD, 0xB8, 0xB3, 0xD2, + 0x6D, 0x02, 0x93, 0xA8, 0xBC, 0xBF, 0x25, 0x6B, 0x5E, 0x5B, 0xB3, 0x31, 0x23, 0x3A, 0x30, 0xDA, 0xF0, 0xFE, 0x4A, 0xDE, 0x80, 0x82, 0xB3, 0x03, 0xC3, 0x9E, 0x55, 0x1D, 0xBC, 0xC3, 0x02, 0xBF, + 0x9B, 0x8A, 0xD3, 0x93, 0x3C, 0xB9, 0xAD, 0x90, 0x0A, 0x68, 0x25, 0x36, 0x7E, 0x15, 0x3E, 0x89, 0x6B, 0xC9, 0xAF, 0xDF, 0x8E, 0x40, 0x55, 0xA9, 0xD0, 0x9B, 0x85, 0x4C, 0xA8, 0x3D, 0x3A, 0xDF, + 0x6E, 0x00, 0x43, 0x75, 0xC4, 0xED, 0xE4, 0xEC, 0x5C, 0x57, 0x80, 0x5F, 0x79, 0xA2, 0x06, 0x03, 0x4C, 0x51, 0x40, 0xCC, 0x60, 0x27, 0x7E, 0xAA, 0x74, 0xCD, 0xEE, 0xE9, 0xF0, 0x49, 0x3E, 0x90, + 0x91, 0xC2, 0x29, 0x98, 0xB6, 0x13, 0x86, 0x3C, 0xE3, 0xAB, 0x77, 0x98, 0x39, 0x2E, 0x69, 0x67, 0x58, 0xC0, 0x32, 0x28, 0x6E, 0x10, 0x39, 0xBB, 0x13, 0x6C, 0x7C, 0x54, 0x30, 0xCB, 0xCD, 0x6D, + 0x99, 0x9A, 0xA1, 0xF7, 0xB2, 0x8B, 0xE6, 0x03, 0x32, 0xCE, 0x70, 0xF5, 0x6E, 0xE3, 0x1C, 0x9E, 0xAB, 0x2D, 0x1E, 0x41, 0x3F, 0x0E, 0x65, 0x59, 0xE1, 0xF5, 0xCC, 0x6A, 0x5A, 0xAA, 0x8A, 0xD2, + 0x64, 0x46, 0x88, 0x85, 0x52, 0x18, 0x1B, 0x8A, 0xA5, 0x30, 0xE4, 0xC6, 0x64, 0x68, 0x01, 0x08, 0x00, 0xAD, 0x5A, 0x94, 0xF3, 0xA0, 0xDD, 0x36, 0x9F, 0x1D, 0x5D, 0x16, 0xA8, 0x3A, 0x5F, 0xF7, + 0x49, 0xC5, 0xFE, 0xC8, 0x67, 0x2F, 0x92, 0xE5, 0xC8, 0x40, 0x0B, 0xD7, 0x67, 0x1F, 0x91, 0xFC, 0x06, 0x97, 0x21, 0x53, 0x14, 0xF0, 0x26, 0x51, 0x61, 0x42, 0xCA, 0xA6, 0x03, 0xED, 0x19, 0x11, + 0x5A, 0xAC, 0x9C, 0x32, 0x5D, 0x18, 0x34, 0x0E, 0x67, 0x62, 0xEF, 0xBA, 0xCF, 0xEF, 0x8E, 0x33, 0x13, 0x3C, 0x0F, 0x8F, 0x84, 0xBE, 0x6C, 0x1F, 0x95, 0xCB, 0x24, 0x45, 0x3D, 0xD8, 0x46, 0xEB, + 0xC6, 0x29, 0x5C, 0x7E, 0x7D, 0xF9, 0x44, 0xB0, 0x17, 0xF1, 0xEF, 0x8A, 0x47, 0x85, 0x22, 0x96, 0xF0, 0x91, 0x96, 0xD1, 0x51, 0xB7, 0x8D, 0x77, 0xC9, 0xC1, 0xDA, 0x7D, 0x99, 0x75, 0xE5, 0x89, + 0x83, 0xD3, 0x31, 0xE1, 0x78, 0x3F, 0xA6, 0x3B, 0xD9, 0x0C, 0x58, 0xC8, 0x2E, 0x4B, 0xFD, 0xDF, 0x8F, 0x0B, 0x4C, 0x37, 0xBB, 0xA4, 0x39, 0x07, 0x4F, 0x32, 0xE4, 0x1A, 0xBB, 0xCC, 0x90, 0xB5, + 0x6C, 0x6A, 0xD3, 0x6E, 0xC8, 0xAB, 0x1F, 0xB3, 0x34, 0xCE, 0x59, 0xDA, 0x0E, 0xEF, 0xBE, 0x46, 0x5B, 0xF9, 0x62, 0x67, 0x4D, 0x25, 0x81, 0x5F, 0x22, 0x10, 0x84, 0x86, 0x56, 0x93, 0xB0, 0x3A, + 0x44, 0xF6, 0x39, 0xF3, 0xA4, 0x7C, 0x36, 0xEE, 0xB2, 0x46, 0xD3, 0x90, 0x7D, 0x2F, 0x1D, 0x23, 0x78, 0xD7, 0xD7, 0x93, 0xD3, 0x95, 0xC3, 0x65, 0x52, 0x5A, 0x46, 0x5D, 0x9C, 0xE4, 0x15, 0x25, + 0x41, 0xE5, 0x94, 0xA7, 0x29, 0xAC, 0x62, 0xEE, 0x4E, 0x3A, 0xB5, 0x89, 0xE7, 0xB0, 0x01, 0xD5, 0xF2, 0x35, 0x4E, 0x3E, 0x30, 0xB1, 0x82, 0xBD, 0x69, 0xDC, 0x5A, 0x87, 0x7F, 0xF1, 0xCB, 0x87, + 0xFB, 0x9C, 0x25, 0x60, 0xBF, 0xE8, 0x2D, 0x3E, 0xDB, 0x06, 0x3B, 0xB7, 0x4D, 0x4B, 0x1F, 0x5C, 0xF3, 0x31, 0xB2, 0xD8, 0x4B, 0x45, 0x98, 0x8E, 0x04, 0xF7, 0x18, 0x32, 0xF0, 0x27, 0x2C, 0xD5, + 0xA8, 0x44, 0x91, 0x9E, 0xC3, 0x41, 0x3A, 0xE0, 0xE9, 0x9F, 0x0A, 0x8D, 0xAD, 0xC1, 0x87, 0xE9, 0xBD, 0x9A, 0x4D, 0xF9, 0xE1, 0x05, 0xD1, 0x81, 0x37, 0x60, 0xC4, 0xFA, 0x32, 0x95, 0xBC, 0x22, + 0x51, 0x7E, 0x89, 0x07, 0xD9, 0x85, 0xD2, 0x79, 0xEA, 0x25, 0x67, 0x4C, 0x78, 0x53, 0x18, 0x80, 0x5D, 0x1D, 0xBC, 0xD7, 0x97, 0x62, 0x46, 0x83, 0xC3, 0x63, 0xEA, 0xCA, 0xFE, 0x62, 0xC0, 0x78, + 0x83, 0x4A, 0x5B, 0x13, 0x78, 0x7F, 0xAF, 0x0A, 0xB3, 0xB4, 0xD2, 0x45, 0x71, 0x3B, 0x02, 0x22, 0x2A, 0x8A, 0x60, 0x56, 0x23, 0xA5, 0xE1, 0xE5, 0x0F, 0x5D, 0xBB, 0xAB, 0x95, 0x6A, 0xBC, 0xA5, + 0xF0, 0x64, 0x11, 0xD5, 0x97, 0xB0, 0xFB, 0x2D, 0x6D, 0xCC, 0x65, 0x0E, 0x77, 0x65, 0xF5, 0xE2, 0x3C, 0x4B, 0x8B, 0xC2, 0xB7, 0xAE, 0x0C, 0x88, 0x58, 0xB6, 0x50, 0xD1, 0x66, 0x89, 0x10, 0x38, + 0x54, 0x39, 0x2C, 0xB2, 0x41, 0x0E, 0xBD, 0x20, 0x8D, 0xF2, 0xE8, 0xD6, 0xF2, 0x21, 0x33, 0xCB, 0x63, 0xBC, 0x21, 0xE9, 0x69, 0xDC, 0x67, 0xA0, 0xE2, 0xEE, 0xDC, 0x42, 0x8E, 0x3B, 0x71, 0xC8, + 0x31, 0x89, 0x9B, 0x8D, 0x41, 0x22, 0xE5, 0x96, 0x69, 0xC1, 0x42, 0xBA, 0xB2, 0x0A, 0xFF, 0x7E, 0xD1, 0x89, 0x54, 0xB6, 0x52, 0x4B, 0x8C, 0x58, 0xD3, 0x91, 0xE3, 0x70, 0x61, 0xD1, 0xD5, 0x66, + 0xEA, 0x04, 0x42, 0x7E, 0x91, 0x44, 0x09, 0x5F, 0xDB, 0x1A, 0x28, 0xC1, 0xFD, 0x49, 0xCA, 0xD9, 0xFD, 0x55, 0xD7, 0x54, 0x7F, 0xF9, 0xD6, 0x0D, 0x54, 0xF7, 0x20, 0x5E, 0xBE, 0xD4, 0x96, 0xD1, + 0xE9, 0xDE, 0xDB, 0x8B, 0x28, 0xCE, 0xF8, 0x1D, 0x1A, 0xA5, 0x78, 0x05, 0x76, 0xD6, 0x7D, 0x70, 0x23, 0x21, 0xE5, 0x89, 0xD4, 0x4A, 0x60, 0xE2, 0x1F, 0xA0, 0x7B, 0xD9, 0x2D, 0xCF, 0xA1, 0x57, + 0xF1, 0x0D, 0xA6, 0x0F, 0xAD, 0x6E, 0x44, 0x28, 0x07, 0xD4, 0xE1, 0xCF, 0x5F, 0x7A, 0xBD, 0x0B, 0xB4, 0xBF, 0x1D, 0x7F, 0xF3, 0x6A, 0x0E, 0x63, 0x6E, 0x30, 0x0C, 0xD8, 0x57, 0x55, 0x33, 0x1B, + 0x22, 0x05, 0x97, 0x87, 0x23, 0xD9, 0xAC, 0xE6, 0xF2, 0xD5, 0x6F, 0xEC, 0x9D, 0x54, 0x59, 0x4C, 0xDB, 0x64, 0x3B, 0x8A, 0x9D, 0x8E, 0x6F, 0x76, 0x5C, 0xCE, 0xEF, 0x28, 0x19, 0xB3, 0xEF, 0x55, + 0xDE, 0x38, 0x9F, 0xDC, 0x00, 0x79, 0x27, 0xD2, 0x22, 0xF1, 0x1D, 0x22, 0x76, 0xDD, 0x18, 0xD4, 0xDF, 0x86, 0xE8, 0xE7, 0xE2, 0xA4, 0xD9, 0x94, 0x3D, 0xD8, 0x83, 0xD7, 0x0B, 0xC0, 0x45, 0xB6, + 0xAF, 0xAB, 0xED, 0xDF, 0x42, 0x18, 0xA2, 0x5A, 0xBF, 0x3F, 0xB0, 0xD4, 0x13, 0xD6, 0x18, 0x37, 0xC4, 0x5B, 0x86, 0xF9, 0xE6, 0xC6, 0x25, 0x53, 0x37, 0xC3, 0x8A, 0xF3, 0x5B, 0xE8, 0x2B, 0xE1, + 0xF0, 0x3A, 0xF0, 0x81, 0x1F, 0x2F, 0x1E, 0xEB, 0x25, 0x27, 0x6B, 0xF6, 0xAB, 0x27, 0xB9, 0x25, 0x64, 0x33, 0x4F, 0x06, 0x3A, 0x83, 0x18, 0xFC, 0x69, 0xC1, 0x34, 0x70, 0xDA, 0x6F, 0xD9, 0x47, + 0xB7, 0xEE, 0x2F, 0x67, 0xA7, 0x60, 0x5F, 0x6A, 0x57, 0x95, 0x3F, 0x96, 0xA3, 0x35, 0xB5, 0x50, 0x12, 0x63, 0x98, 0x67, 0x49, 0x02, 0x11, 0x88, 0x62, 0xF0, 0x86, 0x3F, 0x93, 0x13, 0xA3, 0x6A, + 0xD0, 0x57, 0x34, 0xE5, 0x1F, 0x54, 0x98, 0x62, 0x17, 0x0E, 0xC3, 0x69, 0x5A, 0x67, 0xE0, 0xC1, 0x6C, 0xDC, 0xDE, 0xA7, 0x7B, 0x39, 0x5D, 0x1F, 0xC4, 0xF8, 0xF1, 0x3A, 0x08, 0xBA, 0x8D, 0x4C, + 0xC4, 0x09, 0xCA, 0xBC, 0x9B, 0x15, 0xF1, 0x00, 0x7A, 0x4E, 0x3E, 0x4A, 0x71, 0x37, 0xB7, 0x00, 0xBE, 0xF5, 0xC3, 0x32, 0x97, 0x73, 0x5B, 0xE4, 0xC0, 0xAD, 0xB5, 0x4A, 0xA2, 0xDB, 0xE0, 0x96, + 0x2D, 0x16, 0x83, 0x55, 0x5C, 0xFC, 0xB8, 0x84, 0x17, 0xD7, 0x19, 0x4B, 0x7A, 0xDF, 0x09, 0xB3, 0xD2, 0xD5, 0xBA, 0xDE, 0xB1, 0xE8, 0x47, 0xAF, 0x62, 0x11, 0x65, 0x45, 0x4C, 0x4D, 0xA0, 0x0D, + 0x11, 0x85, 0x06, 0xE8, 0x25, 0xBD, 0x8F, 0x90, 0xDE, 0x0C, 0xC1, 0x1A, 0xFA, 0xD8, 0x5E, 0x08, 0xE9, 0x0E, 0xB5, 0xC4, 0x42, 0xD5, 0xB8, 0x5C, 0x9A, 0x9B, 0x86, 0xF2, 0x75, 0x8F, 0x4B, 0xB9, + 0xDA, 0x95, 0xA7, 0xB5, 0xB5, 0x85, 0xD6, 0x1A, 0x5C, 0x0E, 0x6E, 0x92, 0x0B, 0xBC, 0x43, 0x64, 0x97, 0xBB, 0x6C, 0x9A, 0xB8, 0x18, 0xAF, 0xCB, 0x5C, 0xE8, 0x14, 0x81, 0x09, 0xED, 0x99, 0x94, + 0x2E, 0x07, 0x90, 0xC5, 0xE2, 0x71, 0x4F, 0x4A, 0x88, 0x06, 0x74, 0xF4, 0xC6, 0x86, 0xF0, 0x7B, 0x48, 0xF5, 0xB8, 0x35, 0x9F, 0x9A, 0xF6, 0x3E, 0xB2, 0x05, 0xA3, 0x7B, 0xC0, 0xC6, 0x39, 0xDF, + 0x09, 0x3F, 0x88, 0xBB, 0x45, 0xCA, 0x1B, 0xA0, 0xDD, 0xD7, 0x1D, 0xB7, 0x4A, 0x22, 0xCE, 0x88, 0x4B, 0x39, 0x83, 0xD4, 0x54, 0xD5, 0x69, 0x56, 0x66, 0xED, 0x88, 0xDB, 0xB1, 0x66, 0xE9, 0x98, + 0x96, 0xEA, 0xBF, 0x67, 0x6B, 0xB8, 0x6D, 0x0E, 0xF3, 0xBD, 0xCF, 0x24, 0x1F, 0x50, 0xF2, 0x67, 0x2E, 0x3C, 0xD3, 0xBD, 0xAE, 0x60, 0xE6, 0xEC, 0xCD, 0xEF, 0x96, 0xDF, 0x63, 0x90, 0x88, 0xE4, + 0x45, 0x7A, 0xEE, 0xE7, 0x74, 0x6C, 0x24, 0xBD, 0x67, 0x6F, 0x3E, 0xFE, 0xA2, 0x7D, 0xDC, 0xDA, 0xC8, 0xA4, 0x1C, 0xA5, 0xBF, 0x9E, 0x03, 0xC8, 0xF5, 0xAF, 0xBB, 0xC8, 0x9B, 0x6D, 0x96, 0xBF, + 0x90, 0xD9, 0x4C, 0xFF, 0xD9, 0x1E, 0x3A, 0x8A, 0x07, 0xCC, 0xF0, 0x44, 0x93, 0xA5, 0xCB, 0x44, 0x1A, 0x9F, 0x59, 0x61, 0xEA, 0xC7, 0x1C, 0xEA, 0xB0, 0x4A, 0x78, 0xF7, 0x0B, 0x4F, 0x52, 0xF4, + 0x63, 0x09, 0x45, 0xAC, 0xC4, 0x5F, 0x4F, 0x83, 0xEE, 0x96, 0x7C, 0xF2, 0xB2, 0x37, 0x5D, 0x0F, 0xCE, 0x3A, 0x3F, 0x6E, 0x43, 0x96, 0x36, 0x14, 0xCC, 0xE0, 0x36, 0x03, 0xF0, 0x59, 0x7D, 0x30, + 0xE1, 0xD6, 0x75, 0xC0, 0x0F, 0x3C, 0xCA, 0xC4, 0x49, 0x21, 0xD2, 0x92, 0x28, 0xFF, 0x52, 0x96, 0xD4, 0x35, 0x25, 0x2F, 0x9C, 0xB3, 0x26, 0xA4, 0xD6, 0xFC, 0x34, 0xF0, 0x79, 0x89, 0xC1, 0x84, + 0x28, 0x86, 0x74, 0x59, 0xD1, 0x82, 0x95, 0xD2, 0xD6, 0x12, 0x10, 0x7F, 0x75, 0x35, 0xED, 0x27, 0xF6, 0x84, 0x6C, 0xA8, 0xD3, 0xB1, 0x73, 0x9D, 0x23, 0x45, 0xD2, 0x8B, 0xCC, 0xC4, 0xFD, 0x1A, + 0x63, 0x14, 0xFD, 0x47, 0x88, 0x9B, 0x53, 0xA1, 0xA7, 0x34, 0x63, 0x4B, 0xEC, 0x0C, 0x0A, 0x1C, 0x8A, 0x0A, 0x89, 0xAC, 0x66, 0xB0, 0xF4, 0xE5, 0x32, 0x8F, 0x76, 0x39, 0x2D, 0x01, 0x73, 0xE1, + 0x74, 0xEB, 0x8F, 0xA6, 0x0F, 0x86, 0xC9, 0x7F, 0x00, 0x20, 0xDC, 0xFA, 0x4E, 0x69, 0x94, 0xFC, 0x08, 0xFD, 0xCF, 0x40, 0x5A, 0x44, 0xB1, 0xC4, 0x8C, 0xC2, 0x1C, 0x51, 0xA0, 0x92, 0x81, 0x73, + 0x71, 0xF9, 0x6E, 0x64, 0xBD, 0x2B, 0x69, 0xBA, 0x79, 0xD7, 0xE4, 0xDD, 0x2C, 0x1F, 0x71, 0x8B, 0xF4, 0x56, 0x39, 0xCB, 0x45, 0x39, 0xE1, 0xF8, 0x9C, 0xF0, 0xE5, 0xEF, 0x25, 0x88, 0xE2, 0x5D, + 0xEB, 0x44, 0x10, 0x1D, 0x3C, 0x12, 0xE1, 0x4B, 0x99, 0x3C, 0x0A, 0xB3, 0x55, 0x61, 0x13, 0x82, 0x19, 0x59, 0xC6, 0xE9, 0xFC, 0x9A, 0xCC, 0x95, 0xBA, 0x17, 0x31, 0x4A, 0xC5, 0x6D, 0x2B, 0x26, + 0xA0, 0x39, 0x10, 0x69, 0x2A, 0xA4, 0xE1, 0x58, 0xF6, 0x81, 0xCB, 0xAA, 0x7C, 0x0F, 0xF8, 0x03, 0xD6, 0x66, 0x4B, 0x60, 0x9E, 0x5A, 0x4A, 0x25, 0x73, 0x58, 0x9F, 0xCD, 0x16, 0x8D, 0x17, 0x90, + 0x13, 0x32, 0x3E, 0x4B, 0x4F, 0x51, 0x53, 0x68, 0x6B, 0x74, 0x75, 0x78, 0x7C, 0xA2, 0xAF, 0xB6, 0xC4, 0xC5, 0xF4, 0xF8, 0x0D, 0x1D, 0x37, 0x46, 0x4D, 0x55, 0x57, 0x6A, 0x7B, 0x8C, 0xAC, 0xB2, + 0xC6, 0xC7, 0xC8, 0xD2, 0xEA, 0xF4, 0xF9, 0xFC, 0x18, 0x19, 0x20, 0x25, 0x27, 0x39, 0x5A, 0x5E, 0x90, 0xA4, 0xAF, 0xE8, 0xEF, 0xF2, 0xF8, 0xF9, 0x11, 0x29, 0x38, 0x68, 0x76, 0xAC, 0xAD, 0xBD, + 0xD6, 0xDA, 0xE1, 0xEB, 0xF3, 0x1B, 0x38, 0x5D, 0x67, 0x76, 0x81, 0x87, 0x8A, 0x91, 0x94, 0xAE, 0xC2, 0xD6, 0xD9, 0xDF, 0xFF, 0x01, 0x02, 0x1B, 0x2F, 0x34, 0x3B, 0x3F, 0x40, 0x58, 0x94, 0xAE, + 0xB1, 0xBD, 0xC5, 0xD5, 0xD7, 0x0A, 0x20, 0x23, 0x2D, 0x30, 0x3C, 0x65, 0x6C, 0x75, 0x76, 0x7E, 0x83, 0x90, 0xC2, 0xE7, 0xEB, 0x0C, 0x51, 0x64, 0x77, 0x88, 0xA4, 0xBB, 0xC1, 0xC7, 0xDB, 0xDC, + 0xE5, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, 0x28, 0x38, 0x45, 0x55, 0x65, 0x75, 0x81, 0x02, 0x10, 0x1C, 0x20, 0x18, 0x40, 0x08, 0x09, 0x06, 0x4C, 0x04, 0x04, + 0x02, 0x85, 0x00, 0x1D, 0xA0, 0x42, 0x9C, 0x48, 0x00, 0x81, 0x8C, 0x40, 0xC1, 0x42, 0x00, 0xC1, 0x0D, 0x09, 0x01, 0x94, 0xE8, 0x78, 0x5E, 0x1F, 0xF5, 0x65, 0x11, 0x03, + }, + }, + { + .name = "Dilithium Round 2, Level 5 (8-7) KAT 1", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_87, + .rho_len = 32, + .rho = { + 0x4B, 0x62, 0x2D, 0xE1, 0x35, 0x01, 0x19, 0xC4, 0x5A, 0x9F, 0x2E, 0x2E, 0xF3, 0xDC, 0x5D, 0xF5, 0x0A, 0x75, 0x9D, 0x13, 0x8C, 0xDF, 0xBD, 0x64, 0xC8, 0x1C, 0xC7, 0xCC, 0x2F, 0x51, 0x33, 0x45, + }, + .seed_len = 32, + .seed = { + 0x13, 0x77, 0x46, 0xE7, 0x45, 0x56, 0x52, 0xAF, 0x6F, 0xB7, 0x64, 0x83, 0x32, 0x42, 0xF0, 0x64, 0xFA, 0xAA, 0xDD, 0x99, 0x3B, 0x49, 0xFE, 0x63, 0xBC, 0xDF, 0xA2, 0xC5, 0x5E, 0xD3, 0xEC, 0xD4, + }, + .tr_len = 48, + .tr = { + 0x83, 0x21, 0xD1, 0x46, 0x16, 0x74, 0x43, 0x38, 0x73, 0xC0, 0xDB, 0x53, 0x59, 0x75, 0xEA, 0xD8, 0x1F, 0x18, 0xBD, 0x73, 0x99, 0xE7, 0xAE, 0xC5, 0x4C, 0xA2, 0xF3, 0x61, 0x91, 0x83, 0xD0, 0xA9, + 0x89, 0x77, 0xFA, 0x2D, 0x99, 0x1C, 0x2C, 0x01, 0x8D, 0xBE, 0xDE, 0xBF, 0xBC, 0x8C, 0xAE, 0x66, + }, + .s1_len = 672, + .s1 = { + 0x1B, 0x86, 0x4D, 0x02, 0xB0, 0x0D, 0x92, 0x34, 0x12, 0x4C, 0xC8, 0x71, 0x93, 0xB0, 0x65, 0x8B, 0x16, 0x4C, 0xC0, 0xA4, 0x89, 0xC9, 0x46, 0x0C, 0x5C, 0x34, 0x44, 0x4A, 0x24, 0x10, 0xD4, 0xB4, + 0x81, 0x8C, 0x04, 0x32, 0xD3, 0x84, 0x00, 0x04, 0xC0, 0x91, 0x8C, 0x04, 0x29, 0xD1, 0x46, 0x91, 0x10, 0x91, 0x20, 0x19, 0x06, 0x24, 0x94, 0x14, 0x2E, 0x64, 0x48, 0x82, 0x0B, 0xA9, 0x90, 0x20, + 0x24, 0x0D, 0x11, 0xC2, 0x05, 0x20, 0xA7, 0x20, 0x98, 0x28, 0x91, 0x60, 0x48, 0x86, 0xD1, 0xA0, 0x44, 0x5B, 0x86, 0x0C, 0x21, 0x89, 0x4D, 0x04, 0x99, 0x08, 0xA4, 0xA4, 0x2C, 0xD0, 0x08, 0x52, + 0x42, 0x42, 0x26, 0x00, 0x31, 0x85, 0x50, 0x12, 0x92, 0x12, 0x91, 0x91, 0x02, 0x14, 0x6E, 0xE3, 0xB2, 0x0D, 0x41, 0x40, 0x68, 0xD8, 0x98, 0x10, 0x9B, 0x84, 0x69, 0x21, 0xB3, 0x05, 0x62, 0x16, + 0x68, 0x22, 0x19, 0x41, 0x44, 0x10, 0x4C, 0x49, 0x94, 0x41, 0x58, 0x46, 0x52, 0x0B, 0x09, 0x04, 0x10, 0x98, 0x29, 0x61, 0xB8, 0x01, 0x01, 0x19, 0x50, 0x23, 0x12, 0x49, 0xDB, 0x02, 0x41, 0x88, + 0x38, 0x66, 0xE4, 0x92, 0x65, 0x9A, 0xA0, 0x08, 0x62, 0x48, 0x2D, 0xC4, 0x94, 0x01, 0xD9, 0xA8, 0x69, 0x18, 0x10, 0x08, 0x4B, 0x14, 0x10, 0x24, 0x08, 0x8C, 0xC8, 0x36, 0x4D, 0x99, 0x20, 0x61, + 0x43, 0x32, 0x68, 0x11, 0x86, 0x48, 0xCB, 0x82, 0x88, 0xC8, 0x16, 0x71, 0x9C, 0xC6, 0x29, 0x63, 0x00, 0x6A, 0x4B, 0x14, 0x84, 0x23, 0xC3, 0x49, 0x1B, 0x11, 0x64, 0xDC, 0x92, 0x05, 0x60, 0x80, + 0x60, 0x22, 0xB3, 0x8C, 0x43, 0x08, 0x11, 0x8C, 0x22, 0x25, 0x41, 0x86, 0x08, 0x20, 0x40, 0x31, 0x8B, 0x12, 0x90, 0x18, 0xB2, 0x28, 0xC3, 0x08, 0x0C, 0x93, 0x00, 0x82, 0x13, 0x00, 0x80, 0x22, + 0x05, 0x8C, 0x12, 0x15, 0x08, 0x22, 0xA2, 0x25, 0xD1, 0x12, 0x68, 0x48, 0x14, 0x6D, 0x93, 0x26, 0x60, 0xDC, 0x02, 0x89, 0x1C, 0x35, 0x8D, 0x8C, 0x22, 0x82, 0x80, 0x98, 0x64, 0xC1, 0x30, 0x30, + 0x02, 0xB5, 0x21, 0x1C, 0x10, 0x30, 0x00, 0x82, 0x24, 0xCA, 0x88, 0x70, 0x4C, 0x08, 0x4E, 0x18, 0x16, 0x46, 0x90, 0x14, 0x62, 0xE3, 0xC6, 0x69, 0xD0, 0x30, 0x42, 0x62, 0x96, 0x91, 0xD3, 0xC4, + 0x8C, 0x41, 0x06, 0x92, 0xCA, 0xA0, 0x11, 0x21, 0x36, 0x81, 0x20, 0xA6, 0x2D, 0x20, 0x14, 0x89, 0xC1, 0x00, 0x42, 0x12, 0x43, 0x2C, 0xD3, 0xA0, 0x85, 0x64, 0x30, 0x8A, 0x59, 0x10, 0x28, 0xE3, + 0x98, 0x11, 0x24, 0xC9, 0x4D, 0x5C, 0x42, 0x00, 0x5C, 0xB0, 0x4C, 0x02, 0xB8, 0x2C, 0x60, 0xA6, 0x01, 0xA3, 0x14, 0x62, 0x83, 0x88, 0x50, 0x24, 0x08, 0x85, 0x92, 0x00, 0x2A, 0x1A, 0xA3, 0x21, + 0x04, 0xC9, 0x89, 0xA3, 0x14, 0x8D, 0xC1, 0x18, 0x0E, 0xCA, 0x48, 0x24, 0x90, 0xA0, 0x8C, 0x13, 0x09, 0x90, 0xA3, 0x48, 0x12, 0x61, 0x30, 0x71, 0x50, 0x86, 0x41, 0x13, 0x11, 0x80, 0xC8, 0x88, + 0x24, 0x1C, 0x99, 0x61, 0x0A, 0x83, 0x64, 0x12, 0xB8, 0x4D, 0xC0, 0x12, 0x80, 0x1B, 0x08, 0x0C, 0x84, 0x82, 0x01, 0xC0, 0x00, 0x0C, 0x03, 0x94, 0x01, 0x04, 0x44, 0x68, 0x00, 0x25, 0x71, 0x5B, + 0x38, 0x71, 0x0B, 0xB3, 0x4C, 0x04, 0xB4, 0x25, 0x83, 0x30, 0x44, 0x60, 0xA2, 0x51, 0x5C, 0xC0, 0x48, 0xA3, 0x30, 0x6A, 0x9B, 0x10, 0x4D, 0x24, 0x24, 0x82, 0xD9, 0x86, 0x44, 0x10, 0x00, 0x64, + 0x1B, 0x31, 0x6D, 0x0A, 0x20, 0x25, 0x41, 0xC0, 0x71, 0xA4, 0x12, 0x91, 0x0C, 0x21, 0x6C, 0xA2, 0x86, 0x61, 0x13, 0xB9, 0x28, 0xC2, 0x14, 0x52, 0x04, 0x29, 0x30, 0x1C, 0xB3, 0x04, 0x02, 0x10, + 0x8E, 0x44, 0x26, 0x65, 0x20, 0x48, 0x8E, 0x1A, 0xC0, 0x29, 0x02, 0xB9, 0x30, 0xE4, 0x22, 0x8E, 0x19, 0xC5, 0x4D, 0x04, 0xB2, 0x8D, 0xDC, 0xB0, 0x0D, 0x53, 0x16, 0x72, 0x42, 0xB6, 0x70, 0x60, + 0x32, 0x32, 0xCA, 0xC2, 0x0C, 0x1C, 0x19, 0x4D, 0x11, 0xA7, 0x2C, 0x23, 0x31, 0x46, 0xA1, 0x82, 0x0D, 0x04, 0x10, 0x64, 0xA1, 0x02, 0x31, 0xE3, 0x04, 0x44, 0x22, 0x37, 0x6A, 0x1C, 0x87, 0x2C, + 0x1A, 0x86, 0x49, 0x9A, 0x48, 0x8E, 0xA0, 0x96, 0x90, 0x0B, 0xB7, 0x64, 0xE2, 0x48, 0x8A, 0xE1, 0x80, 0x08, 0x22, 0x14, 0x11, 0x0A, 0x05, 0x86, 0x41, 0x34, 0x0D, 0x00, 0xB0, 0x40, 0xCC, 0x32, + 0x0A, 0x4C, 0x36, 0x4E, 0x22, 0xC5, 0x29, 0x84, 0x48, 0x70, 0x00, 0x84, 0x81, 0xE1, 0x10, 0x85, 0xDC, 0x30, 0x29, 0xE2, 0x38, 0x2E, 0x91, 0x40, 0x81, 0x04, 0x90, 0x64, 0x9A, 0xB0, 0x01, 0x12, + 0xB5, 0x04, 0x8C, 0x34, 0x31, 0x21, 0x00, 0x4E, 0xD3, 0x28, 0x68, 0x23, 0xC9, 0x4D, 0xD3, 0x16, 0x8E, 0x21, 0x91, 0x90, 0x12, 0x87, 0x29, 0x23, 0xA7, 0x48, 0x04, 0xC0, 0x81, 0x08, 0x26, 0x09, + }, + .s2_len = 768, + .s2 = { + 0x48, 0x32, 0x46, 0x09, 0x10, 0x4D, 0x04, 0x05, 0x70, 0x59, 0x92, 0x20, 0x59, 0x44, 0x0A, 0x58, 0x42, 0x65, 0x91, 0x34, 0x72, 0x14, 0x23, 0x6D, 0x8C, 0x38, 0x2D, 0x80, 0x92, 0x69, 0x21, 0x90, + 0x6D, 0x10, 0xC0, 0x50, 0x12, 0x86, 0x49, 0xC2, 0xB2, 0x40, 0x9B, 0x34, 0x90, 0x5B, 0x08, 0x8A, 0x98, 0x44, 0x68, 0xDB, 0x22, 0x71, 0xC3, 0x34, 0x51, 0x09, 0xC4, 0x71, 0x4A, 0x82, 0x04, 0x94, + 0x24, 0x02, 0x1A, 0x36, 0x88, 0x4A, 0x48, 0x02, 0x91, 0x02, 0x6E, 0x8A, 0x22, 0x2C, 0x61, 0xA2, 0x80, 0x20, 0x99, 0x28, 0x54, 0x14, 0x31, 0x22, 0x31, 0x6C, 0x0C, 0xB1, 0x21, 0xA3, 0x08, 0x71, + 0x88, 0x34, 0x22, 0xD3, 0x44, 0x6C, 0x02, 0x44, 0x0A, 0x8A, 0x80, 0x71, 0x80, 0x14, 0x6C, 0x9B, 0x42, 0x50, 0xC3, 0x34, 0x72, 0xC9, 0xA2, 0x90, 0x58, 0x44, 0x71, 0x43, 0x00, 0x00, 0x44, 0x34, + 0x0D, 0xD3, 0xC8, 0x8C, 0xA1, 0x26, 0x70, 0x41, 0xC2, 0x24, 0x03, 0x35, 0x52, 0x58, 0xB2, 0x71, 0x09, 0x43, 0x4C, 0x1A, 0xB4, 0x91, 0xDA, 0xC6, 0x85, 0x89, 0xC6, 0x91, 0x23, 0x24, 0x8A, 0x40, + 0x34, 0x4D, 0x19, 0x15, 0x84, 0x14, 0x48, 0x8D, 0xD3, 0x30, 0x20, 0x80, 0xC8, 0x61, 0x93, 0x38, 0x0D, 0x88, 0x26, 0x8E, 0x12, 0x47, 0x21, 0x21, 0x19, 0x26, 0x09, 0x42, 0x64, 0x19, 0xA0, 0x84, + 0x02, 0xC0, 0x70, 0x88, 0x98, 0x29, 0xC0, 0x00, 0x2A, 0x53, 0x22, 0x85, 0x90, 0x08, 0x8D, 0xD0, 0x30, 0x40, 0x1C, 0x13, 0x0C, 0x00, 0x86, 0x90, 0x62, 0x28, 0x32, 0x1C, 0x27, 0x20, 0x49, 0x42, + 0x22, 0x8A, 0x02, 0x29, 0xCB, 0xC0, 0x49, 0x44, 0x00, 0x4E, 0x11, 0x19, 0x8D, 0x13, 0x07, 0x72, 0x60, 0x86, 0x04, 0x5A, 0x28, 0x52, 0x88, 0xA4, 0x71, 0x0A, 0xB5, 0x31, 0x12, 0x21, 0x04, 0x9C, + 0x28, 0x81, 0x00, 0x35, 0x6C, 0x64, 0x34, 0x0A, 0x14, 0x92, 0x71, 0xE3, 0x10, 0x72, 0x00, 0x96, 0x4C, 0x24, 0x43, 0x45, 0xCA, 0x24, 0x2C, 0x5B, 0x34, 0x30, 0xA0, 0x96, 0x24, 0x14, 0x29, 0x89, + 0x1B, 0x08, 0x01, 0x80, 0xC6, 0x8C, 0x12, 0x15, 0x71, 0x13, 0x16, 0x44, 0x12, 0xB0, 0x49, 0x4A, 0x00, 0x91, 0x10, 0x80, 0x08, 0x93, 0xB0, 0x40, 0xCC, 0xB6, 0x01, 0x89, 0xC8, 0x20, 0xC9, 0xC2, + 0x84, 0x8B, 0xB8, 0x08, 0x18, 0x96, 0x2D, 0x1B, 0x11, 0x32, 0x83, 0xA6, 0x69, 0x11, 0x07, 0x45, 0x81, 0x14, 0x31, 0x0C, 0x36, 0x4A, 0x0A, 0x01, 0x82, 0x51, 0xA2, 0x10, 0xA3, 0x00, 0x52, 0x44, + 0x28, 0x45, 0x60, 0x12, 0x8D, 0x80, 0x06, 0x64, 0x18, 0xC2, 0x2D, 0x13, 0x93, 0x24, 0x1A, 0x20, 0x68, 0xCB, 0xB0, 0x0D, 0x58, 0xB0, 0x31, 0x94, 0x44, 0x8A, 0xC2, 0x36, 0x06, 0x90, 0x80, 0x64, + 0x61, 0x92, 0x81, 0x98, 0xB0, 0x04, 0x93, 0x12, 0x21, 0xA0, 0xB0, 0x25, 0x22, 0x19, 0x69, 0x1B, 0x29, 0x8D, 0xC2, 0x44, 0x4E, 0xD2, 0x14, 0x04, 0xA1, 0x90, 0x0D, 0x4C, 0x28, 0x26, 0x0C, 0x07, + 0x8C, 0x83, 0x30, 0x50, 0xE2, 0xC6, 0x29, 0x5A, 0x94, 0x00, 0x12, 0x15, 0x00, 0xC9, 0x04, 0x04, 0xC8, 0x42, 0x4A, 0xC4, 0x10, 0x61, 0xC9, 0xC0, 0x31, 0xCC, 0x00, 0x2E, 0xC0, 0x22, 0x8A, 0x18, + 0x05, 0x92, 0x50, 0x84, 0x41, 0x21, 0x81, 0x28, 0x13, 0x18, 0x70, 0xD1, 0x00, 0x11, 0x03, 0x22, 0x06, 0x04, 0x91, 0x65, 0x14, 0x84, 0x4D, 0x62, 0x28, 0x8E, 0x23, 0x96, 0x2C, 0xC3, 0x84, 0x30, + 0x0B, 0x21, 0x4E, 0x18, 0x27, 0x2A, 0x42, 0x16, 0x21, 0x62, 0xB8, 0x31, 0x22, 0x43, 0x40, 0x94, 0x22, 0x2D, 0x11, 0x06, 0x62, 0x80, 0x02, 0x85, 0x44, 0x86, 0x08, 0x41, 0x46, 0x41, 0x40, 0xC8, + 0x4C, 0x5C, 0xC6, 0x50, 0xE1, 0x08, 0x01, 0x0A, 0x21, 0x80, 0x9B, 0xA0, 0x49, 0x19, 0xB7, 0x24, 0x19, 0x18, 0x66, 0x01, 0x81, 0x6D, 0x40, 0xC0, 0x69, 0x52, 0x24, 0x6C, 0x02, 0xA4, 0x00, 0x40, + 0xB8, 0x50, 0x18, 0x37, 0x65, 0xD1, 0x90, 0x84, 0x21, 0x03, 0x25, 0x41, 0x34, 0x45, 0x60, 0x94, 0x41, 0xDA, 0xC0, 0x84, 0x81, 0x22, 0x6A, 0xC2, 0x48, 0x52, 0x1B, 0x36, 0x2A, 0xE3, 0x28, 0x8A, + 0x59, 0xA6, 0x25, 0x03, 0xB4, 0x90, 0x0B, 0xB5, 0x29, 0xC0, 0x44, 0x04, 0x89, 0xB0, 0x2C, 0x83, 0x18, 0x22, 0x20, 0xB9, 0x68, 0xD4, 0x42, 0x62, 0x4A, 0xA2, 0x2C, 0x01, 0x12, 0x4E, 0xCC, 0x48, + 0x80, 0xD3, 0x96, 0x09, 0x02, 0xC6, 0x64, 0x81, 0x32, 0x29, 0x02, 0x84, 0x0C, 0x1B, 0xA1, 0x2D, 0x24, 0x23, 0x09, 0x88, 0x90, 0x25, 0xC8, 0xB6, 0x69, 0x54, 0xB2, 0x25, 0xDC, 0xA6, 0x2C, 0x09, + 0x45, 0x46, 0x88, 0xB6, 0x91, 0x14, 0x87, 0x28, 0x18, 0xC7, 0x2D, 0x1A, 0x85, 0x05, 0x4C, 0x14, 0x82, 0xDB, 0x14, 0x01, 0x20, 0x44, 0x6D, 0x4B, 0x28, 0x2E, 0x8C, 0x00, 0x29, 0x13, 0x41, 0x84, + 0x19, 0x13, 0x8D, 0x00, 0x94, 0x8D, 0x98, 0x82, 0x29, 0x04, 0x23, 0x4E, 0xC1, 0xA2, 0x28, 0x12, 0xC4, 0x70, 0x8B, 0xA8, 0x09, 0xDA, 0x08, 0x65, 0x62, 0x10, 0x81, 0x20, 0x03, 0x8A, 0x80, 0x34, + 0x4A, 0x20, 0xC9, 0x88, 0x22, 0x94, 0x11, 0xC8, 0x92, 0x89, 0xD4, 0xC4, 0x41, 0xA1, 0xB4, 0x84, 0x93, 0x02, 0x89, 0x12, 0x23, 0x41, 0x13, 0xB7, 0x25, 0x49, 0x36, 0x2A, 0x0C, 0xB3, 0x40, 0x49, + 0x36, 0x70, 0x10, 0x41, 0x00, 0x19, 0xB7, 0x09, 0x22, 0x39, 0x8D, 0x63, 0x40, 0x80, 0xA3, 0x94, 0x28, 0x90, 0x04, 0x41, 0x40, 0x18, 0x89, 0x12, 0x47, 0x61, 0x83, 0x12, 0x4E, 0x1A, 0x48, 0x2E, + }, + .t0_len = 3584, + .t0 = { + 0x75, 0x48, 0xEF, 0x27, 0x75, 0xAA, 0x88, 0x5A, 0xB6, 0x93, 0x11, 0x4A, 0x06, 0x0F, 0x01, 0xDC, 0x38, 0x75, 0xEB, 0x2F, 0x16, 0x52, 0xD4, 0x2F, 0x8B, 0x5F, 0x3C, 0xC2, 0xBC, 0xAB, 0x20, 0x9A, + 0xD5, 0xFD, 0x34, 0x18, 0xAC, 0x20, 0x93, 0x0D, 0x7B, 0xA9, 0x80, 0xCB, 0xCC, 0xA8, 0x4C, 0x5F, 0x2F, 0xEE, 0x1F, 0x3F, 0x9B, 0x28, 0x19, 0x28, 0x74, 0x9C, 0x2E, 0x1B, 0xF1, 0x7C, 0x8A, 0x14, + 0x04, 0x6B, 0x24, 0xFA, 0x37, 0x08, 0x83, 0x9B, 0xB4, 0xEE, 0x75, 0x8C, 0xD2, 0xEA, 0x55, 0x64, 0xA2, 0x0F, 0x21, 0xA2, 0x3B, 0xAE, 0x26, 0xDE, 0x9F, 0x9B, 0xC0, 0x42, 0xF9, 0xD4, 0xF2, 0x59, + 0xBB, 0x1A, 0xDD, 0x41, 0x80, 0xF6, 0x73, 0x5D, 0xC5, 0xD3, 0x26, 0x1D, 0xF9, 0xD0, 0xA3, 0x1F, 0xAB, 0x24, 0xED, 0x65, 0x47, 0x32, 0x73, 0xF7, 0x63, 0xD7, 0xBC, 0x48, 0x30, 0xCE, 0xE9, 0xA1, + 0x5E, 0x8F, 0xAE, 0x6E, 0x06, 0x85, 0x34, 0x56, 0x3D, 0x34, 0x71, 0x88, 0xAA, 0xD7, 0xBC, 0x6B, 0xD6, 0x12, 0x68, 0x49, 0x00, 0x44, 0xEB, 0x30, 0x0B, 0x47, 0xA0, 0xCD, 0x78, 0xBC, 0x26, 0x31, + 0x41, 0xAA, 0xEB, 0x3B, 0x96, 0xF4, 0x08, 0x9B, 0x38, 0x5B, 0x46, 0x53, 0x37, 0x29, 0xDE, 0xAA, 0x68, 0x4E, 0x01, 0xAB, 0xD6, 0xE8, 0x9A, 0xFF, 0xF3, 0xBD, 0xAE, 0x91, 0xD4, 0x04, 0x5E, 0x0F, + 0x4A, 0xED, 0x84, 0xD3, 0x18, 0xC6, 0x83, 0x45, 0x7B, 0x88, 0xEA, 0x50, 0x1F, 0xAA, 0x75, 0x13, 0x23, 0x35, 0x07, 0xE3, 0xE7, 0x77, 0xD5, 0xFD, 0x43, 0x48, 0xA9, 0xAB, 0xBC, 0xB8, 0x41, 0x0A, + 0x47, 0x81, 0xD9, 0x45, 0x60, 0x83, 0x0E, 0x3A, 0x61, 0xE6, 0xB3, 0xE0, 0xB8, 0x09, 0xE9, 0x34, 0x47, 0xD3, 0x74, 0x08, 0xD3, 0x1B, 0x90, 0x7F, 0x72, 0xBE, 0xAE, 0x2F, 0x66, 0x3B, 0xE2, 0xC7, + 0xFF, 0xF3, 0xE0, 0x7E, 0xF3, 0xB8, 0x5D, 0x69, 0xA4, 0xF8, 0x7C, 0x4F, 0x2F, 0x07, 0xF7, 0xED, 0x77, 0x69, 0xF9, 0x19, 0xA2, 0xBD, 0xEE, 0xE1, 0x7E, 0x65, 0xA7, 0x30, 0x9D, 0xE5, 0x9D, 0x2B, + 0x0F, 0xA0, 0x5A, 0xB4, 0xAA, 0x92, 0xBA, 0xC3, 0x52, 0xD1, 0xE3, 0x97, 0x7E, 0xB8, 0xE4, 0x66, 0x22, 0x6D, 0x5A, 0xCE, 0x95, 0x51, 0x05, 0x8C, 0x8E, 0xC4, 0x67, 0x7D, 0x03, 0x95, 0xC2, 0x88, + 0xE2, 0xFE, 0xC4, 0xAA, 0x85, 0x46, 0x18, 0xED, 0x25, 0xFF, 0xA9, 0x2E, 0x59, 0xBD, 0xD0, 0xAB, 0x72, 0x50, 0x34, 0x58, 0xA8, 0x89, 0x79, 0x81, 0x68, 0x8A, 0xB5, 0x4E, 0x92, 0x8D, 0x11, 0x1E, + 0x7D, 0x62, 0x19, 0x27, 0x57, 0xA5, 0xA3, 0xFC, 0x5C, 0xB6, 0xBC, 0x2A, 0x89, 0xC2, 0x8D, 0x40, 0x41, 0x04, 0x4C, 0x0E, 0x75, 0x04, 0x07, 0xBB, 0x05, 0xFE, 0xF1, 0xF6, 0xF4, 0x59, 0xED, 0x35, + 0x72, 0xB2, 0x69, 0x70, 0xF8, 0x3C, 0xDF, 0x6D, 0x88, 0x62, 0x9D, 0x43, 0xEF, 0x95, 0x5E, 0x85, 0x13, 0x5C, 0x13, 0x8A, 0x67, 0x36, 0xAC, 0x4E, 0xB1, 0xD3, 0x48, 0x1F, 0xCD, 0x14, 0x06, 0x4B, + 0x03, 0x45, 0x81, 0x04, 0x6F, 0x47, 0x57, 0xA8, 0x4F, 0x6F, 0x36, 0x7C, 0x31, 0x58, 0xCE, 0x87, 0xD6, 0x59, 0x9B, 0xEB, 0x20, 0xA9, 0x20, 0xCD, 0xEE, 0xF8, 0xD6, 0xCC, 0x12, 0xB7, 0xD9, 0x50, + 0x15, 0xED, 0x10, 0xD4, 0xA9, 0xB2, 0x80, 0xEE, 0x82, 0x61, 0xC9, 0xD9, 0x58, 0x3E, 0xC3, 0xCF, 0xCB, 0x31, 0xAC, 0x4F, 0x6B, 0x99, 0x3B, 0xF7, 0xC3, 0xE4, 0x49, 0x2B, 0xF9, 0x82, 0xA2, 0x8D, + 0x54, 0x44, 0x5B, 0x76, 0x1B, 0xDD, 0x7B, 0x6D, 0x7E, 0x53, 0x78, 0x70, 0x9F, 0xCD, 0xDB, 0x00, 0x18, 0x1A, 0xC3, 0xE9, 0x54, 0xA5, 0x5C, 0xCA, 0x5F, 0xE5, 0x24, 0x4A, 0x7B, 0xD7, 0xDA, 0x86, + 0xC6, 0xA5, 0x09, 0x01, 0xEB, 0xC6, 0xBC, 0xBD, 0xF3, 0xC1, 0xBD, 0x5A, 0x8A, 0xB4, 0x86, 0xAF, 0x90, 0xC2, 0x35, 0xC8, 0xCF, 0xA1, 0xD7, 0x72, 0xD3, 0x15, 0xA2, 0xCA, 0x08, 0x3A, 0x9C, 0x58, + 0x28, 0xB6, 0x87, 0xC9, 0x86, 0x07, 0xAE, 0xD4, 0xFD, 0xE6, 0x4E, 0x17, 0x2C, 0x35, 0xC0, 0x5A, 0x8B, 0xF5, 0xB2, 0xF4, 0x84, 0xDD, 0x47, 0xD9, 0x6D, 0x9D, 0xC7, 0xB7, 0x76, 0x56, 0xFD, 0x9F, + 0x8B, 0xA3, 0x9A, 0xB5, 0xEB, 0x46, 0x28, 0x9A, 0x3E, 0x95, 0x30, 0x25, 0x6A, 0x2E, 0x05, 0x6A, 0xE0, 0x05, 0xA7, 0xCD, 0xEC, 0x89, 0x5D, 0xD3, 0x20, 0xDE, 0x82, 0xA1, 0xE1, 0x3A, 0x25, 0x07, + 0x8B, 0xCE, 0xA8, 0x38, 0x8F, 0x22, 0x04, 0xB5, 0x38, 0x1D, 0xB8, 0xC9, 0xB2, 0x4D, 0xAA, 0x79, 0x3D, 0x8B, 0x94, 0x84, 0x43, 0xDC, 0xF3, 0x32, 0x84, 0xA4, 0x37, 0x1E, 0x10, 0x1C, 0xF6, 0xE3, + 0x04, 0x1F, 0xC5, 0x41, 0xFF, 0x18, 0xD1, 0xE4, 0xC6, 0x72, 0x9E, 0x44, 0xB9, 0xBA, 0xCA, 0x61, 0xF4, 0x7E, 0xD5, 0x94, 0x93, 0x19, 0x6C, 0xFF, 0xEA, 0x45, 0x8C, 0xF2, 0x27, 0xCF, 0x84, 0x85, + 0x55, 0xCB, 0x92, 0x1C, 0xAB, 0x40, 0xEB, 0xF6, 0x66, 0xD7, 0xA9, 0xA7, 0x0A, 0xC7, 0x04, 0x6A, 0x60, 0x63, 0x45, 0x16, 0x1F, 0x36, 0x55, 0x87, 0xC1, 0xC0, 0x5F, 0x84, 0x5A, 0x8C, 0x39, 0x57, + 0xF1, 0xC8, 0x76, 0x4F, 0x29, 0xF7, 0xA8, 0xFC, 0x56, 0x03, 0xA0, 0x9E, 0x10, 0xF6, 0x82, 0xAF, 0xB3, 0x4E, 0xDE, 0xB3, 0xEA, 0xC5, 0x77, 0xDA, 0x3F, 0x94, 0xD0, 0xBF, 0x15, 0x3C, 0xB6, 0xC3, + 0xAF, 0xDD, 0x69, 0xA4, 0xCA, 0xF2, 0xC8, 0xD3, 0x1D, 0x09, 0x0B, 0xD3, 0x08, 0xD7, 0x12, 0x50, 0x90, 0x63, 0x27, 0x37, 0xC6, 0xAC, 0xE8, 0x6A, 0x3D, 0x8C, 0xAC, 0xBD, 0xCF, 0x8E, 0xAB, 0x94, + 0x5C, 0x07, 0xE6, 0x4E, 0x8E, 0x08, 0x42, 0xBA, 0xCE, 0xCA, 0xBA, 0x6B, 0x31, 0xF5, 0x8C, 0x96, 0xD2, 0x7A, 0x15, 0xF4, 0xDE, 0xAF, 0x85, 0x33, 0x5B, 0xB8, 0x3E, 0xFB, 0x83, 0x39, 0x02, 0x9D, + 0xDC, 0xF2, 0xC2, 0xD9, 0x3D, 0x93, 0x57, 0x02, 0xDA, 0x86, 0x65, 0xE4, 0xC0, 0xE1, 0xC3, 0xFD, 0x4F, 0xF0, 0x44, 0x2A, 0xD5, 0xE8, 0x92, 0xD8, 0x96, 0x95, 0x29, 0x37, 0xA2, 0xC2, 0xC7, 0x7C, + 0x50, 0x69, 0x8E, 0x13, 0x31, 0x4B, 0xAE, 0x4A, 0x12, 0x25, 0x97, 0x26, 0x7F, 0x8D, 0xCD, 0x92, 0x41, 0x0C, 0x5F, 0x7C, 0xFB, 0x3C, 0xA1, 0x97, 0xA2, 0x85, 0x38, 0xDF, 0x23, 0xAF, 0x8D, 0x92, + 0xFD, 0xF1, 0xD7, 0xEC, 0x65, 0xF7, 0xAB, 0x52, 0x8D, 0xEB, 0xD7, 0x69, 0x20, 0x34, 0x68, 0x11, 0x43, 0xE9, 0x42, 0x64, 0x04, 0x58, 0x6C, 0x7B, 0xF1, 0xBD, 0xC0, 0x6A, 0xEC, 0x6F, 0x6D, 0x5B, + 0x69, 0x91, 0x7A, 0x0A, 0x02, 0xE6, 0x15, 0xB9, 0xDB, 0x54, 0x6B, 0x6C, 0x7D, 0xB8, 0xFD, 0xA7, 0x2A, 0x70, 0x7F, 0x36, 0x4F, 0x3D, 0x8B, 0x78, 0x85, 0xE4, 0x04, 0x35, 0x35, 0xE1, 0x55, 0x82, + 0x3C, 0x12, 0xA4, 0xC6, 0x9D, 0x63, 0xDC, 0x82, 0xAC, 0x85, 0x03, 0x4C, 0x98, 0x41, 0x91, 0x8D, 0xA4, 0x8B, 0xDA, 0xA0, 0x9A, 0x80, 0x29, 0x55, 0x1C, 0xF4, 0x35, 0xD2, 0x2A, 0x07, 0xB0, 0x00, + 0x7F, 0xCC, 0x0F, 0x13, 0xC6, 0xFF, 0x1E, 0x19, 0xF9, 0xA9, 0xD6, 0x4B, 0x86, 0xE8, 0xFA, 0xD6, 0x3A, 0xAA, 0xDD, 0xCC, 0xFD, 0x14, 0x08, 0x54, 0x27, 0x43, 0x3F, 0x27, 0xE3, 0x3B, 0x54, 0x30, + 0x57, 0xEE, 0x79, 0x98, 0x18, 0x8B, 0xDD, 0x4D, 0xAF, 0x90, 0x47, 0xCC, 0x46, 0x1A, 0x3E, 0xDF, 0x45, 0x3D, 0x2F, 0xD4, 0xCD, 0x99, 0x26, 0xC6, 0x56, 0xB7, 0xC1, 0xB3, 0x8F, 0x5A, 0xEF, 0xC0, + 0x11, 0x84, 0x2D, 0x1E, 0x7D, 0xCD, 0x0B, 0xC2, 0x6D, 0xCC, 0xC6, 0x0B, 0x62, 0xEB, 0xEC, 0x8D, 0x0E, 0xD3, 0xAE, 0x69, 0x96, 0x59, 0xA4, 0xEB, 0xA4, 0xAF, 0x7A, 0xF4, 0x4D, 0x96, 0x99, 0x9E, + 0xE3, 0x55, 0x46, 0x9D, 0x75, 0x0C, 0x0B, 0xAF, 0xDD, 0xFA, 0x2E, 0xBD, 0xD2, 0x77, 0xF0, 0x2D, 0x3E, 0xBA, 0xB6, 0x8D, 0xA6, 0x52, 0xD3, 0x35, 0x99, 0xB6, 0xEC, 0x02, 0x34, 0x10, 0x37, 0x4B, + 0xCD, 0x33, 0x07, 0x06, 0xA7, 0x1B, 0xA6, 0x81, 0x35, 0x06, 0xD6, 0x08, 0x68, 0xA4, 0xC6, 0xFF, 0x7B, 0xA5, 0xA2, 0x36, 0x7E, 0x0E, 0x54, 0x79, 0x64, 0x36, 0x01, 0x2A, 0xD2, 0x27, 0x74, 0xFE, + 0x63, 0x82, 0x27, 0x9C, 0x32, 0x39, 0x61, 0xCC, 0xFD, 0x10, 0x87, 0xEF, 0x2B, 0xCC, 0xEB, 0x49, 0xC8, 0x71, 0xCE, 0x3C, 0x6A, 0x73, 0x7F, 0xA5, 0xEA, 0xB5, 0x35, 0x77, 0x3A, 0x60, 0x69, 0x42, + 0xFA, 0xA7, 0xF5, 0xE1, 0xE5, 0x88, 0x5D, 0x8F, 0xC1, 0x70, 0xD8, 0xC0, 0x1A, 0x44, 0x93, 0x9E, 0x76, 0x80, 0x06, 0xA1, 0xE0, 0x7C, 0xD4, 0x31, 0x61, 0xB7, 0x55, 0xB0, 0xB9, 0x18, 0x1B, 0x87, + 0x08, 0xDD, 0x50, 0x65, 0xD9, 0xE8, 0x81, 0xB2, 0xE7, 0xAE, 0xAE, 0x9F, 0x60, 0xBD, 0x6E, 0xE5, 0x9B, 0x5C, 0x62, 0x7C, 0x55, 0xEB, 0x5D, 0x6B, 0xF3, 0x3C, 0x27, 0xC3, 0xFA, 0xF3, 0x4C, 0xEE, + 0xC1, 0xF6, 0xAA, 0x96, 0x93, 0xF3, 0xB5, 0x11, 0x58, 0xCA, 0x91, 0x91, 0x7B, 0xD0, 0x63, 0x02, 0x96, 0xB8, 0x5F, 0x08, 0x2E, 0xBC, 0x6F, 0x3F, 0x09, 0x28, 0x07, 0x49, 0x26, 0xD0, 0xAD, 0x77, + 0xBA, 0xA3, 0x62, 0x4C, 0xD5, 0xFC, 0xB2, 0xB8, 0x1A, 0xFC, 0x35, 0xE6, 0x55, 0x2E, 0x4F, 0xF4, 0xA7, 0xEB, 0xE0, 0x02, 0x51, 0x66, 0x16, 0xE9, 0xDB, 0x33, 0x11, 0x80, 0x8C, 0x38, 0xEE, 0xD2, + 0x42, 0xBC, 0x62, 0x8F, 0x93, 0x7F, 0xD8, 0x01, 0xC5, 0x54, 0x7D, 0xB2, 0xAE, 0xF9, 0x67, 0xE4, 0x85, 0x85, 0x03, 0x3D, 0xCC, 0x40, 0x71, 0x6D, 0xB4, 0x56, 0x11, 0xCA, 0x2E, 0xDF, 0xCB, 0xAC, + 0x20, 0x2D, 0xD7, 0xA4, 0x71, 0xFF, 0xF7, 0xB5, 0xE1, 0x56, 0x18, 0xB0, 0x53, 0x24, 0x63, 0xBC, 0x9C, 0xBD, 0x36, 0x25, 0xE5, 0x9B, 0x43, 0x65, 0x7F, 0x5E, 0x97, 0x5B, 0x07, 0x32, 0x4A, 0x86, + 0x21, 0x68, 0xCF, 0x26, 0x83, 0xC6, 0x75, 0x33, 0x91, 0xE6, 0xC0, 0xF9, 0xC0, 0xEA, 0xD9, 0x37, 0x32, 0x08, 0x44, 0xBE, 0xF4, 0xF6, 0xDE, 0xC9, 0x6F, 0x73, 0x6C, 0x3E, 0xDE, 0x48, 0x66, 0x60, + 0xE5, 0x46, 0xF8, 0xF9, 0xBD, 0xBD, 0xB8, 0x85, 0x34, 0x3C, 0x46, 0xC7, 0x29, 0xFA, 0x8D, 0x9A, 0x4D, 0x8B, 0xE2, 0x2C, 0xC0, 0x5D, 0xDE, 0x83, 0xF8, 0xC1, 0x87, 0xC6, 0xF6, 0xC5, 0xE5, 0xB8, + 0x5B, 0x1D, 0x0B, 0xB7, 0xEB, 0x2C, 0xB1, 0xAD, 0x93, 0xB9, 0xEF, 0xC9, 0x26, 0xAE, 0xDB, 0xF8, 0x8A, 0x8F, 0x6E, 0x42, 0x1D, 0x41, 0xAD, 0x9A, 0x1F, 0x57, 0x5D, 0x08, 0xE7, 0x1A, 0x07, 0xFF, + 0x54, 0xFE, 0x6B, 0xCC, 0xDA, 0xDA, 0xCA, 0xE3, 0x62, 0x95, 0x88, 0xF6, 0xAC, 0xEE, 0xCF, 0x99, 0x27, 0xE0, 0xC8, 0xA8, 0xE3, 0x50, 0xFB, 0x2B, 0xF0, 0x71, 0xBF, 0x62, 0xC6, 0x76, 0xEC, 0xA8, + 0x00, 0xC6, 0xAC, 0x69, 0x00, 0xF0, 0x10, 0xCC, 0x17, 0x10, 0xCD, 0x43, 0x7A, 0x11, 0xC9, 0x93, 0xB9, 0x3F, 0xD9, 0xCE, 0x9A, 0x7C, 0xB5, 0x63, 0x13, 0x4F, 0x8C, 0xF0, 0x7A, 0x88, 0x2A, 0xC1, + 0x20, 0x92, 0xFC, 0x45, 0x71, 0x5F, 0x74, 0xEF, 0x9C, 0xBA, 0x1F, 0x52, 0xD3, 0x5E, 0x3E, 0xA4, 0x48, 0x78, 0xC4, 0x56, 0x35, 0xEF, 0xA3, 0xD7, 0xFA, 0xB5, 0xED, 0xE9, 0x74, 0xFB, 0xFA, 0xF4, + 0x36, 0x61, 0x93, 0x3A, 0x01, 0x40, 0xCF, 0xA5, 0x87, 0x1A, 0xEB, 0x27, 0xD7, 0x5D, 0x05, 0x07, 0xFF, 0xD4, 0x41, 0x09, 0x3D, 0x9F, 0x71, 0x32, 0x49, 0x73, 0x90, 0x64, 0x6E, 0x67, 0xDA, 0x55, + 0x6C, 0xD7, 0x9C, 0xAB, 0x31, 0xC1, 0x6B, 0x86, 0x9B, 0x14, 0xAF, 0x9F, 0xD9, 0xF6, 0x0E, 0xB7, 0x71, 0x73, 0x96, 0x28, 0x0D, 0x98, 0x52, 0x68, 0x18, 0x51, 0xE2, 0x7B, 0x88, 0xD4, 0x46, 0xF6, + 0x05, 0x7C, 0x04, 0x1F, 0x1B, 0xAB, 0xD7, 0x5F, 0xDE, 0xCA, 0x14, 0x51, 0x91, 0x61, 0x4E, 0x9B, 0xCD, 0x98, 0x52, 0xE2, 0xF2, 0x7B, 0x5C, 0xAF, 0x0B, 0x7D, 0x85, 0x1B, 0x8B, 0x75, 0xFF, 0xB4, + 0x24, 0x40, 0x22, 0x0C, 0xD4, 0x91, 0xCE, 0x8C, 0x9E, 0xFE, 0xA8, 0x36, 0x5B, 0xA7, 0xCF, 0x05, 0x05, 0xD2, 0x07, 0xA8, 0xD9, 0x35, 0x67, 0x52, 0x95, 0xBC, 0x82, 0x55, 0xDB, 0xB8, 0x22, 0xD0, + 0xCB, 0x29, 0x7D, 0x36, 0xEB, 0x50, 0xE8, 0x33, 0x07, 0x66, 0xF3, 0x53, 0x83, 0xAE, 0x91, 0xF5, 0x79, 0x7D, 0x70, 0x2A, 0x1D, 0x45, 0x16, 0xDE, 0x66, 0x35, 0x92, 0x7A, 0xEC, 0x0F, 0x66, 0xA1, + 0xC1, 0x0B, 0x1C, 0xDB, 0xF8, 0x23, 0x89, 0xDA, 0xE9, 0xAD, 0x73, 0x4D, 0x53, 0x2C, 0x83, 0x2C, 0xA6, 0xDB, 0xAF, 0x4B, 0xD0, 0x57, 0xDB, 0x6A, 0x92, 0xE2, 0x8D, 0x41, 0x11, 0x35, 0xA2, 0x92, + 0x50, 0x80, 0xE9, 0x2F, 0x8F, 0x2C, 0xD1, 0xEC, 0xD7, 0x00, 0xFB, 0xF4, 0xE2, 0x4F, 0x00, 0xAE, 0xA8, 0xBF, 0x37, 0x15, 0xE7, 0xE0, 0x43, 0xD1, 0x43, 0x0F, 0xDC, 0x8F, 0x08, 0x61, 0x63, 0x8A, + 0x91, 0xA0, 0xA1, 0x4A, 0xDB, 0x38, 0x7A, 0x07, 0x9F, 0x78, 0xBA, 0x85, 0x25, 0x77, 0x1A, 0x54, 0x97, 0x7D, 0x35, 0x7F, 0x4C, 0x98, 0x90, 0xE5, 0xAE, 0xD7, 0xB4, 0x88, 0xE9, 0x3D, 0x55, 0x6B, + 0x1B, 0x12, 0x12, 0xA1, 0x81, 0xBC, 0x0B, 0xFC, 0x47, 0xEA, 0x47, 0x2B, 0x02, 0x9A, 0xF5, 0x54, 0x2A, 0x2C, 0x87, 0x7D, 0xA2, 0x84, 0x6B, 0x60, 0x5D, 0x40, 0x6B, 0x3A, 0xF6, 0xE9, 0xDD, 0x9C, + 0xE5, 0xC1, 0x80, 0x13, 0xE1, 0x52, 0xE6, 0x54, 0xBF, 0x31, 0x0E, 0xE9, 0x81, 0xAD, 0x99, 0x1F, 0x4A, 0xDD, 0x6E, 0xFB, 0xC1, 0x68, 0x82, 0x8A, 0x17, 0x64, 0xB1, 0x80, 0xE4, 0x1F, 0x77, 0xFD, + 0xE5, 0xF8, 0x29, 0x7D, 0x76, 0xEB, 0xD5, 0xC1, 0xBE, 0x90, 0x3C, 0xA6, 0xF6, 0x7C, 0x3A, 0xD4, 0xF4, 0x8B, 0xC8, 0x25, 0xF5, 0x9E, 0x22, 0x8C, 0xBC, 0xAA, 0x8F, 0xC8, 0xEA, 0x24, 0x6C, 0xB8, + 0x1A, 0xC5, 0x08, 0xBD, 0x99, 0x3E, 0x2B, 0x3E, 0xC0, 0xAE, 0xF7, 0x88, 0x0B, 0x68, 0xE6, 0xB9, 0xC9, 0x2D, 0x6A, 0x86, 0x39, 0x09, 0xF1, 0x48, 0x79, 0x02, 0x03, 0x37, 0x21, 0xB4, 0xE2, 0x5E, + 0xF8, 0x90, 0x99, 0xE5, 0x37, 0x6B, 0xE2, 0x0A, 0x98, 0x6E, 0x15, 0x28, 0xD8, 0xF0, 0xC1, 0x1E, 0xC4, 0xF3, 0x9D, 0x42, 0xA4, 0x56, 0xE8, 0x74, 0x1E, 0x2B, 0x00, 0x02, 0xFA, 0xC3, 0x67, 0xAC, + 0x9D, 0xC0, 0xE5, 0x52, 0x4C, 0xBC, 0x43, 0x6F, 0xE6, 0x22, 0x62, 0xCB, 0x46, 0x34, 0xAA, 0x3E, 0xC7, 0x3A, 0xF8, 0xC4, 0x88, 0x95, 0x90, 0xBF, 0x48, 0xDF, 0x21, 0xE4, 0x2B, 0x14, 0x02, 0x1A, + 0x41, 0xA3, 0xCC, 0x11, 0xEE, 0xBC, 0x91, 0xBA, 0x2F, 0xFB, 0xB5, 0xEE, 0x3C, 0x24, 0x0D, 0xB2, 0xA0, 0xE7, 0x04, 0x58, 0x85, 0x73, 0x6F, 0xDA, 0x1B, 0x1F, 0x7A, 0x02, 0x7C, 0x67, 0x2E, 0x12, + 0x4D, 0x1E, 0x6F, 0x89, 0x39, 0xDE, 0x75, 0xC0, 0xD0, 0x97, 0x37, 0x11, 0xDD, 0xBC, 0x93, 0x90, 0xE1, 0xC8, 0x5B, 0x4A, 0x22, 0xCB, 0xE0, 0x03, 0x74, 0xBA, 0xB4, 0xE4, 0xDF, 0xA5, 0xAA, 0x37, + 0x26, 0x75, 0x6B, 0xDD, 0x00, 0xFF, 0x42, 0x9E, 0x4F, 0xB8, 0x0D, 0x77, 0x4E, 0xB2, 0xC6, 0x4B, 0xC6, 0x6E, 0x04, 0x2E, 0xC3, 0x62, 0x1A, 0xDB, 0x4C, 0xE2, 0x00, 0xBF, 0x88, 0x5B, 0x7B, 0x75, + 0x6F, 0x25, 0x0E, 0x73, 0x32, 0x3A, 0xB5, 0x17, 0x5E, 0x83, 0xA7, 0xB7, 0x31, 0xD5, 0xAE, 0x85, 0xB5, 0xC9, 0x8E, 0xC2, 0xF7, 0x0D, 0x30, 0x26, 0x47, 0x9E, 0x0B, 0x68, 0xEA, 0x67, 0xF5, 0xB8, + 0xFF, 0x1D, 0xFB, 0x63, 0xE9, 0x40, 0xB7, 0x86, 0xD9, 0x3E, 0x35, 0x1F, 0x8C, 0xDC, 0x94, 0x79, 0x19, 0x6A, 0xA8, 0xD7, 0x84, 0x26, 0xAB, 0x0E, 0x65, 0x03, 0x19, 0x90, 0xD0, 0xFE, 0xF6, 0xF6, + 0x41, 0xFF, 0xE6, 0x87, 0x7F, 0x31, 0x0D, 0xD4, 0xFA, 0x50, 0xD4, 0xB4, 0x18, 0xB4, 0x96, 0x36, 0x2F, 0x30, 0xED, 0x54, 0x7B, 0xBD, 0x70, 0x1C, 0x67, 0xB4, 0xB7, 0x6A, 0xBA, 0x94, 0xAD, 0x52, + 0x9E, 0xF3, 0x72, 0x38, 0xA1, 0x3D, 0xB9, 0x1D, 0xBC, 0x97, 0xDA, 0xD3, 0x40, 0x6D, 0x3B, 0xB4, 0x33, 0x0F, 0xA5, 0xE4, 0x6F, 0x19, 0x37, 0xF3, 0xFE, 0x70, 0xEB, 0xB1, 0x6A, 0x7D, 0x53, 0x28, + 0x93, 0x22, 0x13, 0xBE, 0x26, 0xE3, 0x06, 0x0F, 0x5D, 0x6D, 0xA2, 0xB7, 0x23, 0x60, 0xC3, 0x6C, 0x1A, 0x06, 0xC3, 0x85, 0x67, 0x48, 0xE3, 0x04, 0xC4, 0xAC, 0x1F, 0xA6, 0x01, 0xBA, 0xB9, 0xD7, + 0x5A, 0x18, 0x02, 0x62, 0x63, 0xB0, 0xCE, 0x54, 0xEF, 0xA3, 0x10, 0xF6, 0x65, 0xE9, 0xC0, 0xB0, 0xF5, 0x8D, 0xE2, 0x60, 0xBF, 0x20, 0xC9, 0x82, 0xCC, 0x67, 0xFC, 0x45, 0xF5, 0x9F, 0x88, 0x1E, + 0x1F, 0xE2, 0xF1, 0x01, 0x9D, 0x6F, 0xC0, 0xE7, 0x3B, 0x7B, 0x6B, 0x31, 0xA3, 0xFB, 0x1A, 0x99, 0x10, 0x5E, 0x2F, 0xF7, 0xDC, 0x97, 0x91, 0xE9, 0xA3, 0xB9, 0x72, 0xDA, 0xC1, 0xE8, 0x58, 0x94, + 0xDE, 0x9D, 0xEC, 0x2B, 0x76, 0xEB, 0xF2, 0xEC, 0xD9, 0x0D, 0x22, 0x9D, 0xA4, 0xB1, 0x80, 0x3F, 0x67, 0xDC, 0x36, 0x34, 0x73, 0x7A, 0x03, 0xA3, 0x58, 0x8B, 0xFC, 0x03, 0x5C, 0x85, 0x0D, 0x22, + 0x97, 0x78, 0xB5, 0xC1, 0x57, 0x36, 0x2C, 0x6B, 0x8A, 0xAA, 0xD4, 0x6B, 0x49, 0xD5, 0xF0, 0xB6, 0x53, 0xC8, 0x9B, 0xFE, 0x01, 0xFA, 0xF3, 0x38, 0x55, 0xFC, 0xA3, 0xD3, 0x8B, 0x00, 0x98, 0xA7, + 0x66, 0x81, 0xCF, 0x99, 0x51, 0xC4, 0x3E, 0x6C, 0xEC, 0x60, 0x93, 0x82, 0x1E, 0x38, 0xB0, 0x64, 0x14, 0x07, 0x8A, 0xB9, 0x5F, 0x83, 0xED, 0x8B, 0x1F, 0x1A, 0xDB, 0x90, 0xDF, 0xEE, 0x9E, 0x52, + 0xA8, 0x56, 0xB9, 0x71, 0xE6, 0xE4, 0x34, 0x72, 0x71, 0x5A, 0xA6, 0xA5, 0x8C, 0x11, 0x20, 0x45, 0x1A, 0xBC, 0x52, 0xBB, 0x65, 0x44, 0xD3, 0x86, 0x9F, 0x5F, 0x4A, 0x18, 0x09, 0x1D, 0xF1, 0xCC, + 0x2C, 0x02, 0x1F, 0xBE, 0x0A, 0x80, 0x8B, 0xE8, 0x6E, 0x70, 0x6C, 0x32, 0x69, 0x1E, 0xBD, 0x0E, 0xFD, 0x32, 0x2E, 0x5A, 0x29, 0xE0, 0xA1, 0x79, 0xB2, 0x77, 0xAD, 0xAA, 0xC5, 0x50, 0x60, 0x35, + 0xD4, 0xD2, 0x3C, 0x31, 0x66, 0xD8, 0x69, 0x27, 0x1A, 0xAD, 0x66, 0x4A, 0xCA, 0x50, 0xEB, 0x62, 0x2E, 0x8D, 0x8A, 0x2D, 0x09, 0xA3, 0x47, 0x72, 0x00, 0x80, 0x0E, 0xF8, 0xDF, 0xDC, 0x01, 0xC3, + 0x06, 0x2F, 0xC9, 0x8E, 0x53, 0x9F, 0x4F, 0x6F, 0xE1, 0x59, 0x4E, 0x92, 0xA2, 0xCF, 0x66, 0xD2, 0x84, 0x97, 0xC1, 0xB4, 0xDD, 0xF5, 0x4A, 0x32, 0x40, 0xC4, 0x06, 0x88, 0xA3, 0xFF, 0x30, 0xBB, + 0x10, 0xFD, 0x97, 0x82, 0xE9, 0xD1, 0x96, 0x6B, 0xD2, 0x2A, 0x23, 0xEA, 0x12, 0xB3, 0xFE, 0xD0, 0xE1, 0xD3, 0x2F, 0x61, 0xEE, 0xFA, 0xEA, 0x7B, 0xB5, 0xEF, 0xBE, 0xE4, 0x10, 0xA8, 0x7A, 0xB0, + 0x79, 0x16, 0x1B, 0x2A, 0xF6, 0xD8, 0x16, 0x47, 0x0E, 0xB8, 0x50, 0xF7, 0x24, 0x70, 0x54, 0xE0, 0xED, 0xB1, 0xD6, 0x56, 0x4D, 0x15, 0xA2, 0x3B, 0xC2, 0xDF, 0x89, 0x6B, 0xEB, 0x07, 0xDE, 0xE2, + 0xE0, 0x2E, 0xC6, 0xC2, 0x4F, 0x12, 0xEE, 0x96, 0x95, 0x75, 0xCA, 0xF3, 0xDD, 0x72, 0x23, 0x52, 0xC9, 0x81, 0x46, 0x4A, 0x9F, 0x5D, 0xED, 0x7E, 0xF3, 0x71, 0x16, 0x1A, 0x8A, 0x62, 0x0C, 0xB4, + 0x29, 0xDE, 0x55, 0x48, 0xE5, 0xC0, 0xE3, 0xBC, 0x2C, 0x3D, 0xBA, 0xB7, 0x93, 0x28, 0xD5, 0xFA, 0x70, 0xA4, 0xF6, 0x99, 0xE5, 0x4D, 0x3C, 0x22, 0x4C, 0xF3, 0xCB, 0xA4, 0x1E, 0x7D, 0xE7, 0xE3, + 0xAF, 0xC3, 0x20, 0xDE, 0xCA, 0x7C, 0x36, 0x2F, 0xAC, 0x7C, 0xC9, 0x26, 0x78, 0x46, 0x4D, 0x41, 0x3D, 0xD4, 0x22, 0x9E, 0x76, 0xAA, 0x90, 0x93, 0x80, 0x9C, 0x0F, 0x5E, 0xDE, 0x53, 0x0A, 0xCB, + 0xFE, 0xCF, 0x08, 0x2B, 0xC5, 0xD2, 0x18, 0xD0, 0xB8, 0xF3, 0xF1, 0x76, 0x89, 0x7A, 0xCF, 0xF3, 0x59, 0xF1, 0xA6, 0xA8, 0x06, 0xB7, 0xA8, 0x66, 0x9C, 0x72, 0xC2, 0x26, 0xF2, 0xB8, 0x45, 0x2E, + 0xC8, 0xD3, 0x5F, 0xA6, 0x6B, 0xFE, 0x93, 0x63, 0xAE, 0x9E, 0x84, 0x42, 0xD1, 0x85, 0x50, 0x80, 0x1B, 0x00, 0x62, 0x24, 0x68, 0x57, 0x3C, 0xAD, 0x37, 0xBD, 0x18, 0x99, 0xC2, 0xAB, 0x37, 0x5F, + 0x98, 0xB0, 0xEF, 0x9C, 0x51, 0x84, 0xD4, 0x0F, 0x23, 0x93, 0x05, 0x4E, 0xCE, 0x1E, 0xAB, 0x24, 0xDE, 0x05, 0x22, 0xFE, 0x0F, 0xDF, 0xF7, 0x01, 0x6E, 0xAF, 0x4F, 0x88, 0xBB, 0x28, 0xF3, 0x64, + 0xAE, 0x4A, 0xD3, 0xDA, 0x4B, 0x70, 0xAC, 0x0E, 0x47, 0xD2, 0xB6, 0x7B, 0x9A, 0x60, 0x37, 0x68, 0x61, 0xC6, 0x7C, 0x6B, 0x85, 0x74, 0xCC, 0x07, 0x83, 0x88, 0x92, 0xC3, 0xC8, 0x55, 0x68, 0x0A, + 0xF6, 0x97, 0x18, 0x9C, 0xFF, 0xD3, 0x7C, 0xA8, 0x3A, 0x33, 0x71, 0x0F, 0x7A, 0xE9, 0xB0, 0xA8, 0x57, 0x95, 0xFC, 0x6E, 0x4A, 0x57, 0x79, 0x1D, 0x93, 0x2D, 0xD1, 0x10, 0x8B, 0x90, 0x86, 0xBB, + 0x3E, 0x29, 0x65, 0x24, 0xE2, 0x91, 0x07, 0xE3, 0x35, 0x4B, 0x4C, 0x40, 0xAD, 0xDB, 0x8C, 0x16, 0x5D, 0xBB, 0xA9, 0x50, 0xFD, 0xCC, 0x0B, 0x3D, 0x92, 0x88, 0x83, 0x9D, 0x9B, 0xA6, 0x35, 0x37, + 0x23, 0x17, 0x73, 0xC6, 0x61, 0xDA, 0xD4, 0x0C, 0xC3, 0xA5, 0xD7, 0xAB, 0x1C, 0x59, 0x43, 0xEA, 0xB0, 0x3C, 0x81, 0xFB, 0x39, 0xB5, 0xA6, 0x7B, 0x04, 0xD3, 0x34, 0x82, 0x88, 0x55, 0x6A, 0xB8, + 0xDA, 0xD4, 0x5E, 0x1D, 0xFF, 0x68, 0x6C, 0x07, 0x12, 0x83, 0x5D, 0xB6, 0x16, 0x6B, 0x2A, 0xDD, 0xA6, 0x2D, 0x95, 0x08, 0x66, 0xCC, 0xE4, 0x9E, 0xD3, 0x71, 0xE8, 0x76, 0x8C, 0x8E, 0x6E, 0x49, + 0xB9, 0x00, 0x0E, 0xA2, 0x93, 0xBD, 0x56, 0x96, 0x87, 0x8F, 0x8C, 0xB1, 0x7C, 0xF8, 0x79, 0xA8, 0x89, 0x7E, 0xD9, 0xDE, 0xD7, 0x74, 0x26, 0x3A, 0x83, 0x0E, 0x4D, 0xEE, 0x2E, 0xD7, 0x52, 0x0B, + 0x4C, 0x59, 0xFF, 0x69, 0x71, 0x1F, 0xB3, 0x5F, 0x67, 0x0D, 0x48, 0x77, 0xC7, 0xD3, 0x12, 0x24, 0xA3, 0xAD, 0xD1, 0x43, 0xAA, 0xB9, 0x65, 0x30, 0xB1, 0x80, 0xE5, 0xFB, 0x5E, 0xC9, 0xD8, 0x3F, + 0x57, 0x1A, 0xB7, 0x94, 0x77, 0xAD, 0xEA, 0x40, 0x9C, 0x2B, 0xA9, 0x86, 0xC7, 0xA0, 0x54, 0xE6, 0x14, 0x8F, 0x03, 0x7D, 0xB9, 0x71, 0x07, 0x92, 0xF6, 0x12, 0x15, 0xA3, 0xFD, 0xF1, 0x28, 0xFF, + 0xA7, 0x15, 0x4F, 0xB0, 0x1C, 0xF4, 0xEF, 0x18, 0xFB, 0xC2, 0xA2, 0x03, 0xBD, 0x37, 0x6D, 0x68, 0x6C, 0x36, 0x70, 0x6F, 0x13, 0x2E, 0x20, 0x81, 0xB9, 0x10, 0xFD, 0x15, 0x46, 0x0C, 0x5A, 0x05, + 0x09, 0x9C, 0x84, 0x23, 0x6F, 0x98, 0x2F, 0xBE, 0xBC, 0x62, 0x51, 0xEB, 0x07, 0x68, 0x88, 0xF9, 0x64, 0xE5, 0x79, 0x94, 0x42, 0x16, 0x0D, 0xA2, 0x60, 0x80, 0x29, 0xD6, 0x1B, 0xE9, 0xAD, 0x99, + 0xB4, 0x5B, 0x7B, 0xEC, 0x36, 0xD7, 0xFA, 0x12, 0xBA, 0x3F, 0x50, 0x28, 0xFD, 0x5B, 0x90, 0xE4, 0x26, 0xB9, 0x04, 0x88, 0x49, 0x92, 0x18, 0x27, 0x9E, 0xCB, 0xDC, 0x33, 0xF1, 0xE7, 0x17, 0xBD, + 0x44, 0x0F, 0x5C, 0x85, 0x80, 0x8D, 0x72, 0x91, 0xF6, 0x36, 0xE8, 0xF5, 0xDE, 0xA6, 0xEA, 0x59, 0x18, 0x6F, 0xFC, 0x6C, 0xF8, 0x59, 0x2A, 0x09, 0x72, 0x46, 0x34, 0xA3, 0x01, 0x8C, 0xA8, 0xE5, + 0x52, 0x5E, 0x3E, 0xC7, 0xAE, 0x6F, 0x01, 0x5E, 0x28, 0x7E, 0xA0, 0x6A, 0x6F, 0x19, 0x3E, 0xB6, 0x50, 0xEC, 0x00, 0x95, 0xAF, 0x8F, 0x43, 0xFE, 0x12, 0x2A, 0xC3, 0xF4, 0x7D, 0xEC, 0xDB, 0x72, + 0xDD, 0x4F, 0x68, 0x69, 0x86, 0x64, 0x5D, 0x61, 0xD9, 0x7D, 0xD6, 0x97, 0x64, 0x9F, 0x1E, 0x7B, 0xE0, 0x17, 0x30, 0xD1, 0xBD, 0xBD, 0xF7, 0x62, 0x71, 0x40, 0xDC, 0x0E, 0x18, 0xE6, 0xB3, 0x55, + 0x7B, 0xA3, 0x67, 0xF0, 0x90, 0xFB, 0xD7, 0xC5, 0x47, 0x5E, 0xD3, 0xFA, 0x05, 0x5B, 0x32, 0x5D, 0x4B, 0x61, 0x35, 0x9F, 0x45, 0xBC, 0xFE, 0xF1, 0xA6, 0x06, 0xC7, 0x2E, 0xF3, 0x62, 0x62, 0xA0, + 0x45, 0x51, 0xBC, 0x8C, 0x24, 0xFA, 0xB3, 0x53, 0x21, 0xFC, 0xE8, 0xBC, 0xE5, 0x56, 0x06, 0x27, 0x9A, 0x29, 0x15, 0x69, 0x76, 0xFB, 0x45, 0xEE, 0x76, 0x1D, 0x92, 0x50, 0x14, 0xCB, 0x69, 0x1F, + 0xF7, 0x6B, 0x5F, 0xEF, 0xE1, 0xB8, 0x39, 0x5B, 0x81, 0x10, 0x6A, 0x24, 0x5C, 0x93, 0x0E, 0x2D, 0x99, 0x54, 0xF1, 0xCC, 0x5A, 0x3A, 0xAA, 0x2C, 0x9C, 0xD5, 0x62, 0xA7, 0xB5, 0xC7, 0x4D, 0x84, + 0xC0, 0xC2, 0xFE, 0xE6, 0x2E, 0x0E, 0xDB, 0xE1, 0xE8, 0xFB, 0x96, 0x90, 0xA2, 0xF4, 0x0B, 0x8D, 0xFD, 0xE1, 0x34, 0xC8, 0xBE, 0xDA, 0x37, 0x0A, 0x7B, 0x17, 0x0D, 0xAA, 0xBC, 0xA6, 0xB9, 0xFE, + 0x48, 0x9E, 0xF4, 0xEA, 0x66, 0x29, 0xF0, 0x3E, 0x5E, 0x44, 0x30, 0xC2, 0xFA, 0x57, 0x31, 0xEB, 0xC7, 0x47, 0x6A, 0xE6, 0x3F, 0xF8, 0x9B, 0x39, 0x49, 0xC9, 0x93, 0x71, 0x77, 0xD3, 0x63, 0x1E, + 0x14, 0xC1, 0x26, 0x57, 0x9F, 0x79, 0x74, 0xD9, 0x6C, 0x37, 0xCD, 0x73, 0x0A, 0x09, 0x8D, 0xFE, 0xCB, 0x6A, 0xFC, 0x86, 0x41, 0x65, 0x66, 0x8F, 0x03, 0xD5, 0x12, 0xA4, 0xCA, 0xDC, 0x49, 0xA4, + 0xEB, 0xEE, 0x2E, 0x1A, 0x26, 0x7E, 0xE2, 0xE2, 0xA7, 0x6B, 0xBB, 0x2C, 0x77, 0x6A, 0x44, 0x87, 0xBC, 0xC0, 0xFC, 0x00, 0xAF, 0xD7, 0xC1, 0x81, 0x7F, 0x7E, 0x89, 0x00, 0x26, 0xD5, 0xD4, 0x25, + 0x4C, 0x9C, 0xCC, 0xBA, 0x2B, 0xB3, 0x01, 0xBA, 0x57, 0xCE, 0x7C, 0xD4, 0x7A, 0xE1, 0x8D, 0x65, 0x3F, 0x9A, 0x92, 0x05, 0x3A, 0xF9, 0x0B, 0xEE, 0xC3, 0xA8, 0x29, 0xB8, 0x52, 0xC2, 0x3D, 0x0D, + 0xF7, 0x52, 0x07, 0x70, 0x1E, 0x67, 0x49, 0x74, 0xED, 0x56, 0x2F, 0xF5, 0x9A, 0x81, 0x1B, 0xB8, 0x5C, 0xCF, 0x62, 0x13, 0x64, 0xCD, 0x9F, 0x87, 0xC9, 0xE7, 0x8B, 0x9D, 0x2F, 0x2E, 0xB2, 0x6F, + 0x00, 0x41, 0xAF, 0x1A, 0x47, 0xA4, 0x37, 0xC4, 0x0C, 0x02, 0x93, 0x9B, 0x62, 0xC8, 0x90, 0x52, 0x13, 0x5A, 0x06, 0x63, 0x2E, 0x43, 0xDE, 0x35, 0x34, 0x8E, 0xEA, 0x91, 0x75, 0x03, 0x47, 0xB8, + 0x6A, 0xC2, 0xFA, 0xB5, 0x55, 0x53, 0x24, 0x9F, 0xC2, 0x5D, 0x2B, 0x57, 0x49, 0x69, 0x92, 0x91, 0x38, 0xA4, 0x83, 0x71, 0xDC, 0x74, 0x6E, 0xAC, 0x5F, 0xA1, 0x08, 0xE2, 0x6C, 0xBC, 0xC5, 0xB6, + }, + .t1_len = 2304, + .t1 = { + 0x1B, 0xEA, 0x94, 0x79, 0x6B, 0xBA, 0xD0, 0x5D, 0xA6, 0xD7, 0xD2, 0x58, 0x1A, 0x10, 0xE9, 0x7C, 0xF1, 0xF8, 0x9D, 0x66, 0xED, 0x7A, 0x7A, 0xE2, 0x3B, 0xBE, 0xB6, 0x8B, 0x87, 0xF5, 0x1E, 0xE2, + 0x69, 0xDA, 0x47, 0x6D, 0x3F, 0xCA, 0x1C, 0xA5, 0x4D, 0x27, 0x26, 0x72, 0xB3, 0x7A, 0x61, 0x11, 0x25, 0x5E, 0x37, 0xA6, 0xF7, 0x71, 0x9B, 0xC2, 0xDD, 0x38, 0x97, 0xC2, 0xA7, 0x74, 0x89, 0x4C, + 0x4B, 0xD8, 0xE6, 0xF5, 0xE7, 0xE1, 0x10, 0xA6, 0xDF, 0x0E, 0x58, 0x44, 0x20, 0x8D, 0x94, 0x11, 0x53, 0xCC, 0xDD, 0x77, 0xA3, 0x4B, 0xBC, 0x37, 0x26, 0xA0, 0x87, 0x85, 0xD7, 0x28, 0x02, 0xE2, + 0xF1, 0x52, 0xB3, 0x30, 0x67, 0x89, 0xB1, 0xEA, 0x50, 0x2D, 0x42, 0x22, 0x71, 0x24, 0x9A, 0xC5, 0x57, 0x11, 0x39, 0xE1, 0x7F, 0x62, 0x9A, 0xF3, 0x5C, 0x9D, 0x7F, 0x43, 0x49, 0x1D, 0x83, 0xCC, + 0x01, 0x07, 0x7C, 0x58, 0x84, 0xC6, 0x2A, 0x1A, 0x87, 0xE7, 0x5E, 0x68, 0x48, 0xE6, 0xD1, 0x2D, 0xC1, 0x3A, 0xE8, 0x43, 0x1A, 0x93, 0xAB, 0xCA, 0xB7, 0x9E, 0x05, 0x2E, 0xFC, 0xAE, 0x5E, 0x02, + 0xF4, 0x49, 0xE8, 0x11, 0x8E, 0x6D, 0x9F, 0x36, 0x9F, 0xDD, 0x0A, 0x59, 0x33, 0x37, 0xE4, 0xC0, 0xC7, 0x50, 0xFE, 0x4A, 0x4F, 0xAE, 0x5F, 0x83, 0xC0, 0x17, 0x93, 0xBF, 0xD7, 0x6E, 0xA0, 0x81, + 0x77, 0xBC, 0xA3, 0x78, 0x71, 0xD9, 0x14, 0x51, 0xC5, 0xA8, 0x19, 0x5A, 0xBB, 0x3C, 0x5B, 0x46, 0xCC, 0x66, 0x08, 0xBE, 0xD7, 0x7E, 0x92, 0x3C, 0xE1, 0x51, 0x64, 0x25, 0x06, 0x54, 0x16, 0x95, + 0xA4, 0xE2, 0x96, 0xCB, 0xC6, 0x4D, 0x3B, 0x32, 0x3F, 0x77, 0xBE, 0x7B, 0x72, 0x4C, 0xC4, 0x38, 0xF0, 0xF7, 0xB6, 0xAC, 0xA6, 0xE1, 0xC9, 0x90, 0x8A, 0xA0, 0x86, 0xF3, 0x0B, 0x3D, 0x3C, 0x0C, + 0x1D, 0xB6, 0x44, 0x90, 0x37, 0xB4, 0x9D, 0x10, 0x67, 0x40, 0xC9, 0xDB, 0x8D, 0x99, 0xC5, 0x7B, 0x49, 0xA7, 0xBC, 0x14, 0xB1, 0x71, 0x07, 0x35, 0xAF, 0x96, 0x1B, 0x77, 0x60, 0xA8, 0x2D, 0xFB, + 0xB1, 0xD8, 0x9C, 0x72, 0xD7, 0x09, 0x4F, 0xC8, 0x95, 0x1B, 0xB0, 0xE9, 0x83, 0x97, 0xD3, 0x25, 0xBF, 0x12, 0x00, 0x1B, 0x04, 0xAC, 0xC6, 0x64, 0x79, 0x28, 0x2C, 0x30, 0x57, 0x47, 0x6D, 0xA0, + 0x5A, 0x3B, 0x76, 0xD7, 0x59, 0x2F, 0xBE, 0xF9, 0xDA, 0x06, 0x0E, 0xBA, 0xF4, 0xF7, 0x33, 0xAE, 0x63, 0x63, 0x76, 0xB7, 0x60, 0x5D, 0x9B, 0xBE, 0x60, 0x52, 0x2E, 0x3E, 0xF0, 0xE8, 0x6A, 0x83, + 0x4F, 0x36, 0xA0, 0xCE, 0xC9, 0x6F, 0xBB, 0x4A, 0x8B, 0xF3, 0x1E, 0xAC, 0x2D, 0x5A, 0x52, 0x3B, 0xF4, 0x84, 0x5D, 0xB6, 0xD4, 0xD8, 0x7C, 0x3D, 0x50, 0xC9, 0xE0, 0x27, 0x52, 0xB6, 0x4F, 0x42, + 0x06, 0x2F, 0x62, 0x5A, 0x19, 0x12, 0x53, 0xFA, 0x7A, 0xA4, 0xA3, 0x6E, 0xED, 0x8E, 0xE9, 0xD9, 0x86, 0xFA, 0x86, 0xC1, 0x3B, 0xB3, 0xF1, 0x7D, 0x64, 0x1B, 0x8B, 0x26, 0x7F, 0x01, 0x36, 0x9A, + 0xD1, 0x27, 0x0D, 0xD5, 0x41, 0x3C, 0x94, 0xEF, 0x0B, 0x77, 0x2D, 0x28, 0x9E, 0x7A, 0xCD, 0xAF, 0x20, 0x75, 0x57, 0x6C, 0xF2, 0x15, 0x7B, 0x5C, 0xFA, 0x48, 0x79, 0x68, 0x66, 0x15, 0xFA, 0xBA, + 0xF3, 0x85, 0x74, 0x35, 0x87, 0x41, 0xB9, 0x02, 0xE1, 0x82, 0x7A, 0xC7, 0x1B, 0x9A, 0xED, 0x0B, 0xBC, 0xEE, 0x5F, 0x85, 0x43, 0xD4, 0x5A, 0xB9, 0xCF, 0x4F, 0xF9, 0xA9, 0x5A, 0x5B, 0xF2, 0x86, + 0x9A, 0x64, 0xBC, 0x68, 0x10, 0xB7, 0x57, 0x46, 0x15, 0x4A, 0x4D, 0xA6, 0x49, 0xD6, 0x9B, 0x3E, 0xA9, 0x53, 0xFF, 0xC9, 0x4F, 0xD2, 0x01, 0x27, 0x22, 0xF9, 0x33, 0x4B, 0x8F, 0xCD, 0x4C, 0x12, + 0x65, 0xEA, 0x60, 0x8B, 0xF5, 0x5B, 0x57, 0xAB, 0x08, 0xBE, 0x22, 0x53, 0xE1, 0x57, 0x40, 0x81, 0xC3, 0xC4, 0xD2, 0xB7, 0x41, 0xC8, 0x80, 0x3E, 0x88, 0x8D, 0xEC, 0x54, 0x85, 0x2B, 0xEF, 0xE9, + 0x35, 0x2C, 0x4C, 0x97, 0xC7, 0x6A, 0xFF, 0xC3, 0x64, 0x98, 0x57, 0x8F, 0xCE, 0x72, 0xE5, 0x82, 0x6A, 0xB4, 0xFC, 0x52, 0xFC, 0x26, 0xF1, 0x1C, 0xF1, 0x23, 0x69, 0xCE, 0xD7, 0x04, 0x63, 0xB0, + 0x84, 0x04, 0x93, 0xDD, 0x67, 0x56, 0x04, 0xB0, 0xAE, 0x0D, 0x22, 0x14, 0xC7, 0x8B, 0x34, 0xEE, 0x32, 0x46, 0x9F, 0x68, 0x37, 0x01, 0x12, 0x4A, 0xC4, 0xF9, 0xB7, 0xF4, 0xFA, 0xE7, 0x6E, 0xDD, + 0xFF, 0x67, 0x81, 0xCB, 0xE1, 0x1B, 0x87, 0x61, 0x32, 0x29, 0x95, 0x0C, 0x77, 0xC1, 0x4E, 0xAA, 0x0D, 0xB1, 0xE3, 0x21, 0xF0, 0x1A, 0x59, 0x3B, 0x60, 0xDE, 0xE0, 0x31, 0x88, 0xB2, 0x07, 0xB2, + 0x41, 0x32, 0x11, 0xF5, 0x95, 0xDB, 0x92, 0x8D, 0xA0, 0x94, 0x4F, 0x45, 0x4F, 0x08, 0xBA, 0xCA, 0xE4, 0x14, 0xD8, 0xBF, 0x25, 0x9E, 0xAF, 0xBE, 0x3F, 0x74, 0x26, 0xD2, 0xBF, 0x94, 0x9D, 0xB2, + 0xCB, 0x67, 0xD5, 0x83, 0x2D, 0xFA, 0x3F, 0xF9, 0xD8, 0x23, 0x72, 0xDE, 0x65, 0x7E, 0x61, 0x7F, 0x67, 0xEE, 0x95, 0xDA, 0xC7, 0xEC, 0xE1, 0x60, 0xBA, 0x14, 0x5C, 0xBA, 0x8E, 0x98, 0xBC, 0x5E, + 0x98, 0x9C, 0x41, 0xD4, 0x87, 0x5A, 0x65, 0x95, 0x9B, 0xBE, 0x28, 0x1C, 0xB6, 0xDA, 0x72, 0x1F, 0xCC, 0x90, 0x29, 0xDA, 0x97, 0xDD, 0xE8, 0x3F, 0x7B, 0x1B, 0x95, 0x9A, 0x1A, 0xD4, 0x04, 0x19, + 0x49, 0x55, 0x12, 0x66, 0xFE, 0xED, 0x89, 0x6E, 0x98, 0x89, 0xE0, 0xAC, 0xF4, 0xF7, 0x61, 0x4D, 0x27, 0xCA, 0x7D, 0x05, 0x2C, 0xDB, 0x7A, 0x22, 0xE4, 0x4B, 0x40, 0x92, 0x4A, 0xF7, 0x27, 0xE9, + 0x16, 0xB9, 0x23, 0x7E, 0xD2, 0x01, 0x7C, 0x61, 0xD0, 0x0E, 0x30, 0x16, 0xD3, 0xBD, 0xFD, 0x8B, 0xFC, 0x4E, 0x73, 0xC6, 0xEC, 0x77, 0x7F, 0x8B, 0x06, 0x87, 0xF4, 0x1F, 0x0F, 0x21, 0xE7, 0xFE, + 0xFC, 0x1A, 0x79, 0x6A, 0xB5, 0x02, 0x63, 0x79, 0x03, 0xE8, 0xA1, 0x8C, 0x6B, 0x9A, 0x1A, 0xF9, 0xDC, 0x30, 0x68, 0x22, 0x41, 0xB5, 0x81, 0x41, 0xC5, 0x82, 0xE9, 0xE8, 0xD6, 0x91, 0x4D, 0xD1, + 0xF4, 0x01, 0xBC, 0x05, 0x18, 0xBE, 0x7F, 0x01, 0x47, 0xB3, 0xA1, 0x35, 0xAB, 0x6D, 0x45, 0x89, 0x3B, 0x07, 0x51, 0xC7, 0xED, 0x8C, 0xA6, 0xE5, 0xA6, 0xF1, 0xAE, 0xFB, 0xD5, 0x52, 0x49, 0x24, + 0x3A, 0x20, 0x77, 0x26, 0x93, 0xCA, 0xEB, 0x7F, 0xA1, 0xE4, 0x86, 0xF4, 0x63, 0x1E, 0xD4, 0x9D, 0x7D, 0xA0, 0x23, 0x18, 0x3B, 0xC2, 0x14, 0xEE, 0x22, 0xD8, 0x94, 0x83, 0xD2, 0xC9, 0xD2, 0x17, + 0x63, 0x79, 0xD8, 0x29, 0x55, 0xE9, 0x2D, 0x93, 0xC0, 0xD4, 0x12, 0x05, 0xAB, 0xAA, 0x72, 0x5E, 0x4D, 0x89, 0x97, 0xCA, 0xB1, 0x4B, 0x45, 0xF0, 0x94, 0xD0, 0xAA, 0xA6, 0x4D, 0x37, 0xBD, 0x82, + 0xA7, 0x4B, 0x3D, 0xFA, 0xA4, 0x04, 0xD9, 0x43, 0x1C, 0x1A, 0x49, 0xDB, 0x8A, 0x29, 0x77, 0xF1, 0xCE, 0x24, 0x5A, 0xB2, 0xB1, 0x23, 0x69, 0xB3, 0x4E, 0xE8, 0xEB, 0x01, 0x7A, 0xE2, 0xF0, 0x7F, + 0xB4, 0xA5, 0x56, 0xF6, 0xE9, 0x44, 0x16, 0xE1, 0xA5, 0x4C, 0x08, 0x50, 0x28, 0x8D, 0x24, 0xBA, 0x57, 0x9F, 0x59, 0xA4, 0xDF, 0xAF, 0xAC, 0xA8, 0xF9, 0x87, 0xD4, 0x29, 0x5F, 0x2F, 0xF6, 0xEC, + 0x31, 0x6A, 0x7E, 0x65, 0xD1, 0xC6, 0x67, 0x79, 0x5B, 0x9E, 0xF9, 0x87, 0x05, 0x25, 0x5A, 0x4B, 0xC3, 0x40, 0x97, 0xBC, 0xDD, 0x99, 0x3B, 0xAE, 0x4D, 0x86, 0x79, 0x6A, 0x79, 0x93, 0x52, 0xB7, + 0xBF, 0xC0, 0xD2, 0x2A, 0xD1, 0x7C, 0x6B, 0x68, 0xA3, 0x5A, 0x2B, 0x1C, 0x6B, 0xA1, 0x70, 0x6B, 0x0F, 0x37, 0xC7, 0xED, 0x09, 0x76, 0xBA, 0x2A, 0xFB, 0xFC, 0xF1, 0x93, 0x0B, 0x77, 0x3C, 0xEB, + 0x06, 0x44, 0x80, 0x18, 0xBD, 0x43, 0x14, 0xBE, 0x3E, 0xF1, 0x35, 0x4F, 0xC2, 0xD1, 0xAA, 0x05, 0xEF, 0xFA, 0x54, 0x46, 0x20, 0x21, 0xC5, 0x20, 0x74, 0xC6, 0xE4, 0xA6, 0x34, 0x65, 0xE4, 0x4F, + 0xBC, 0x53, 0xBC, 0x64, 0x3E, 0x48, 0x5E, 0xD0, 0xAD, 0xE0, 0x76, 0xFB, 0xB4, 0x9F, 0x0F, 0x64, 0xA3, 0xE2, 0x2E, 0xD1, 0xF8, 0xCD, 0x91, 0xC1, 0x18, 0xFB, 0x30, 0x61, 0x12, 0x0F, 0x20, 0x3F, + 0xC9, 0x25, 0x7C, 0xE3, 0x06, 0xA5, 0x63, 0x78, 0x73, 0xD5, 0x4B, 0x68, 0x13, 0xD5, 0xA6, 0xFF, 0x60, 0x4A, 0x8B, 0xA2, 0x5F, 0xEB, 0x1E, 0xD1, 0xF8, 0x07, 0xEB, 0x93, 0x9D, 0xA4, 0x5D, 0xBD, + 0xE0, 0xE6, 0xE3, 0x1B, 0x57, 0xC7, 0x6E, 0xF0, 0xD3, 0x3D, 0x93, 0x61, 0x20, 0xA6, 0x43, 0x3D, 0xE5, 0xA4, 0x03, 0x97, 0xF5, 0x01, 0x8A, 0x49, 0x21, 0x34, 0x57, 0x23, 0xA1, 0xB5, 0xEF, 0x49, + 0x06, 0xB7, 0x15, 0x10, 0x1A, 0x01, 0x72, 0x8E, 0x00, 0x1A, 0x1A, 0x95, 0xE4, 0x36, 0x66, 0xFF, 0xE4, 0x39, 0x3F, 0xC9, 0xB8, 0x72, 0xE7, 0x72, 0x9E, 0x9F, 0x4B, 0x50, 0x82, 0xF3, 0xB8, 0x41, + 0x82, 0x58, 0xBB, 0x97, 0xE7, 0x36, 0x0A, 0xE5, 0x8A, 0xAC, 0x97, 0x6A, 0xE9, 0x20, 0xCD, 0xA1, 0x59, 0x2B, 0xF4, 0x2B, 0x06, 0x9E, 0x70, 0x10, 0x5D, 0x08, 0x18, 0x2A, 0x32, 0x57, 0xED, 0xAF, + 0x75, 0x5D, 0x98, 0xF0, 0xFF, 0x20, 0xD1, 0x39, 0xD1, 0x9C, 0x1D, 0x3E, 0x8F, 0xD4, 0x24, 0x60, 0x94, 0x20, 0xAC, 0x86, 0x00, 0x31, 0x76, 0x18, 0xF5, 0x1F, 0xEB, 0x55, 0xBA, 0x8C, 0xD0, 0x2C, + 0x2F, 0x8F, 0x0C, 0x54, 0xB2, 0x0D, 0x4A, 0xA2, 0xC3, 0xBB, 0x82, 0x65, 0xA7, 0x37, 0x51, 0x27, 0xBD, 0x11, 0x84, 0xBE, 0x38, 0xC1, 0xD4, 0x71, 0x2A, 0x58, 0x95, 0x63, 0x82, 0x35, 0x08, 0xC6, + 0x9B, 0x3C, 0xDF, 0x66, 0x0E, 0x4F, 0x7E, 0x4B, 0x45, 0xBA, 0xAA, 0x30, 0x90, 0xE3, 0x75, 0xCE, 0x59, 0xB8, 0x44, 0xE4, 0x37, 0x7B, 0x4B, 0x46, 0xD9, 0x4B, 0x5A, 0x22, 0x7C, 0x20, 0x7A, 0xB9, + 0x4B, 0x55, 0xE0, 0x67, 0xFF, 0x5B, 0xF3, 0xEB, 0xCE, 0x81, 0x0A, 0x7B, 0x92, 0xB9, 0xF4, 0xD3, 0xB5, 0xAC, 0x98, 0xEF, 0x1A, 0x17, 0x5A, 0xD2, 0xC4, 0x39, 0x1B, 0xAC, 0x9A, 0x70, 0xE1, 0xA6, + 0x25, 0x56, 0x3A, 0x9D, 0x5B, 0x59, 0x44, 0x80, 0x1D, 0xD2, 0xDB, 0xCC, 0xFC, 0xDB, 0xE2, 0xD7, 0xA5, 0x17, 0x4F, 0xF3, 0xD1, 0xFC, 0x61, 0xED, 0x47, 0x87, 0xEA, 0x99, 0x17, 0xDC, 0x27, 0x23, + 0x6F, 0x7B, 0x38, 0x30, 0x65, 0xD7, 0xB3, 0x8E, 0x28, 0xC1, 0x03, 0xF6, 0xDD, 0x72, 0x8E, 0xB2, 0x88, 0x23, 0x58, 0xB0, 0x36, 0xA6, 0xB1, 0xE7, 0xFD, 0xC3, 0x77, 0x1F, 0xD1, 0xFE, 0xD5, 0xFF, + 0xA2, 0x59, 0x6D, 0x2B, 0x9F, 0xD8, 0xDA, 0x08, 0x92, 0xE2, 0x42, 0x7C, 0xA0, 0x87, 0xE9, 0xFE, 0x17, 0x4A, 0x66, 0x57, 0xA1, 0x8D, 0xC6, 0x69, 0x4C, 0x7D, 0x73, 0x7E, 0x49, 0xD2, 0xC6, 0x8D, + 0x07, 0xA2, 0x3B, 0x51, 0xC7, 0x67, 0xF4, 0x66, 0x5F, 0xCB, 0x85, 0x5A, 0x9B, 0x8C, 0x84, 0xC4, 0xD7, 0x08, 0x2E, 0x3C, 0x5A, 0x73, 0x4B, 0xBA, 0xF8, 0x45, 0x76, 0x64, 0x74, 0x0A, 0x51, 0x73, + 0xEE, 0xB6, 0x8A, 0xC4, 0xFB, 0x83, 0x4B, 0x16, 0x14, 0x8A, 0xAE, 0x1E, 0xAA, 0xFE, 0xC3, 0x42, 0x73, 0x0C, 0xB8, 0x7B, 0xDD, 0x1F, 0xAB, 0xAE, 0xAC, 0xA9, 0xA0, 0x55, 0x0D, 0xCD, 0x92, 0x4F, + 0xCD, 0x70, 0x0A, 0xCF, 0x2B, 0xB8, 0x30, 0x5B, 0xD9, 0x90, 0xDE, 0x98, 0x89, 0xE7, 0xDF, 0x95, 0x7A, 0x70, 0xEF, 0x25, 0xEA, 0xFF, 0x34, 0x52, 0xFE, 0xFA, 0xEC, 0xFB, 0x1C, 0x20, 0x9E, 0xD6, + 0x98, 0xB9, 0x29, 0x5D, 0x24, 0xCA, 0x18, 0xF6, 0xEF, 0xFC, 0x1F, 0x38, 0xD4, 0xED, 0x7E, 0x9E, 0x2E, 0x60, 0x6D, 0x94, 0x7D, 0xF2, 0x6C, 0x5E, 0xEA, 0x72, 0xDD, 0x3A, 0xED, 0x4D, 0xDB, 0x17, + 0xA6, 0x9E, 0x96, 0xAE, 0xE7, 0x3C, 0x7A, 0xFD, 0xA6, 0xD5, 0x52, 0x8C, 0xE8, 0x50, 0xF6, 0x4A, 0x0F, 0xDF, 0x91, 0x13, 0xA4, 0x04, 0xE8, 0xB7, 0x89, 0x72, 0xD1, 0x1A, 0x5E, 0x05, 0x6C, 0x14, + 0xA8, 0x8E, 0x64, 0x72, 0x58, 0x47, 0xC8, 0x23, 0x80, 0x3A, 0xEE, 0xC9, 0x7E, 0x51, 0x4E, 0x21, 0xCC, 0x6F, 0xDA, 0x9B, 0xF8, 0x04, 0x9B, 0xEA, 0x60, 0x23, 0xAF, 0x26, 0xBD, 0xCD, 0xA4, 0x35, + 0x33, 0xD2, 0x72, 0xE6, 0xF8, 0x34, 0x53, 0x85, 0xBA, 0x73, 0x96, 0x40, 0x26, 0x53, 0x6C, 0x87, 0x65, 0xE5, 0xD3, 0x27, 0x45, 0x64, 0x4E, 0xE3, 0x86, 0x4B, 0xD1, 0xE3, 0x24, 0x85, 0xA3, 0x16, + 0x42, 0xBE, 0xDF, 0x6B, 0x18, 0xD9, 0x41, 0xF3, 0x77, 0x79, 0x11, 0xB5, 0x97, 0xB3, 0x3E, 0xD0, 0x70, 0xA1, 0x8F, 0x5E, 0xD1, 0x29, 0x69, 0xD5, 0xF2, 0xAD, 0x3B, 0xDF, 0x30, 0xD4, 0xDB, 0xE1, + 0x14, 0x48, 0x90, 0x12, 0xEE, 0xB7, 0x77, 0x6C, 0x81, 0x5D, 0x79, 0x9B, 0xBC, 0xDA, 0x08, 0xC8, 0xB1, 0xD6, 0x92, 0xBC, 0x7E, 0x50, 0x1A, 0x79, 0x24, 0x91, 0x98, 0x29, 0xD1, 0x8E, 0x24, 0x07, + 0xDB, 0x13, 0xDC, 0x7C, 0xB2, 0x4E, 0xB1, 0x50, 0xC4, 0x3C, 0x69, 0x5C, 0xC9, 0xD6, 0xBA, 0x71, 0x4E, 0xB2, 0x3F, 0xF7, 0xE5, 0x37, 0x7B, 0x9D, 0xE1, 0x88, 0x95, 0xB4, 0xF9, 0x29, 0x7D, 0x9F, + 0x60, 0xDD, 0xA9, 0x76, 0x3B, 0x93, 0xAB, 0xB9, 0xBD, 0x3B, 0x8A, 0x0D, 0x82, 0xB2, 0xF1, 0x97, 0xAC, 0x68, 0xA1, 0xA2, 0xC1, 0xFE, 0x93, 0xF9, 0x7F, 0xCD, 0x03, 0x5D, 0x97, 0x3A, 0x9C, 0x8E, + 0xD4, 0xD5, 0x48, 0x71, 0x1E, 0x24, 0xE8, 0x59, 0x46, 0x75, 0xDE, 0x0C, 0xD3, 0x51, 0x76, 0x69, 0x49, 0xE6, 0x91, 0x78, 0x57, 0x0B, 0xEE, 0x83, 0xF9, 0xB4, 0x51, 0x0E, 0x39, 0x14, 0xD2, 0x7D, + 0x4E, 0xEF, 0xF2, 0x79, 0xC3, 0x08, 0x3F, 0x65, 0x2B, 0x87, 0x17, 0x24, 0x16, 0xB1, 0x70, 0x4C, 0x75, 0xA6, 0x9D, 0x05, 0x14, 0x91, 0xD6, 0x2A, 0x36, 0x11, 0x8D, 0x5F, 0x3B, 0x76, 0x1E, 0x32, + 0xBA, 0x0E, 0x5C, 0x65, 0xEE, 0x2C, 0x81, 0xA9, 0xF5, 0xB5, 0x55, 0xC8, 0x50, 0x89, 0x18, 0xBB, 0xC0, 0x02, 0x09, 0xCD, 0xBD, 0x6C, 0x54, 0x06, 0xA8, 0xCC, 0x1C, 0x00, 0x29, 0x24, 0x0D, 0x10, + 0x76, 0xE7, 0x22, 0x3E, 0x26, 0x89, 0x8C, 0x27, 0xC9, 0x75, 0x07, 0x97, 0xD6, 0x41, 0xF6, 0x5F, 0x2C, 0x92, 0x4A, 0x07, 0xCF, 0xCD, 0x02, 0x46, 0x1C, 0x7A, 0x27, 0x51, 0x91, 0xDA, 0x37, 0x2E, + 0x33, 0x9A, 0xCD, 0xDA, 0x38, 0xFA, 0x3B, 0x01, 0x4F, 0x06, 0x7E, 0xBD, 0x22, 0x31, 0xE1, 0x87, 0xD6, 0x0B, 0xB7, 0x37, 0xB7, 0x5D, 0x3E, 0xEA, 0x8C, 0x88, 0xB6, 0xA1, 0xEB, 0xCF, 0x8B, 0x25, + 0xAF, 0xCB, 0xB0, 0x71, 0x23, 0x6F, 0x64, 0x40, 0xE5, 0x65, 0xCB, 0xF3, 0xAF, 0x26, 0x32, 0xA2, 0xC9, 0xF6, 0x2F, 0xF3, 0x8B, 0xD8, 0x82, 0x08, 0x08, 0xE8, 0xAB, 0x59, 0x29, 0xED, 0x2B, 0x16, + 0x9A, 0x7F, 0xE8, 0xB8, 0x3C, 0x92, 0x59, 0x19, 0xC9, 0xBC, 0xAA, 0x4B, 0x2F, 0xE6, 0x4F, 0x4D, 0x4C, 0xED, 0x8F, 0x0F, 0xC9, 0xAA, 0xD8, 0x54, 0xC3, 0xE7, 0x5D, 0xF0, 0x51, 0x3C, 0x5E, 0x24, + 0x76, 0x4E, 0xAD, 0xEE, 0x40, 0xA1, 0xCA, 0xE8, 0x9C, 0x42, 0x56, 0xF4, 0x44, 0x54, 0x1A, 0x51, 0x54, 0x5A, 0xCE, 0xEC, 0x09, 0xA9, 0xA0, 0xD8, 0xF4, 0x81, 0xC5, 0xE1, 0x56, 0x90, 0xE7, 0x49, + 0x67, 0x40, 0x98, 0x13, 0x99, 0x5D, 0x02, 0x6F, 0x02, 0x02, 0x38, 0x5F, 0xBF, 0x7D, 0xDA, 0x81, 0x74, 0x79, 0x1E, 0x9E, 0x28, 0xA9, 0x01, 0x04, 0x76, 0x54, 0xE0, 0xAE, 0x54, 0x5A, 0x90, 0xAC, + 0x56, 0xA1, 0x92, 0x3A, 0x8D, 0x83, 0xAB, 0x8D, 0x08, 0x5B, 0x49, 0xC5, 0xBA, 0x0A, 0xBB, 0x68, 0x3E, 0x72, 0xBA, 0x9F, 0x03, 0xFC, 0xC7, 0x20, 0x01, 0x24, 0x40, 0x87, 0xF4, 0xF9, 0xB7, 0xE2, + 0xE9, 0xD0, 0xE8, 0x20, 0x66, 0x44, 0xC1, 0x36, 0x60, 0xD2, 0x81, 0xBD, 0x7B, 0xB1, 0x65, 0x32, 0x86, 0x38, 0xFF, 0xA3, 0x13, 0x60, 0x0B, 0x30, 0x85, 0xDE, 0x3B, 0x9A, 0xA2, 0x20, 0xBA, 0xD0, + 0x3C, 0x08, 0x90, 0xFA, 0x3C, 0x90, 0x0E, 0x49, 0x16, 0x21, 0x87, 0xC0, 0x2E, 0x7E, 0xD7, 0x3D, 0xCF, 0x50, 0xF5, 0xB0, 0x8C, 0xA5, 0xEB, 0x8E, 0xDE, 0x36, 0x7A, 0x28, 0xAE, 0x94, 0xFF, 0x29, + 0xB3, 0x62, 0x98, 0x72, 0xAD, 0x99, 0xEA, 0x2B, 0x22, 0x67, 0x37, 0x4D, 0xDB, 0x56, 0x41, 0x29, 0x80, 0x3A, 0x78, 0xDA, 0xBE, 0xC9, 0x07, 0x16, 0xC3, 0x13, 0xF7, 0xAB, 0xCE, 0xC4, 0xD3, 0x43, + 0x0E, 0x2E, 0xC3, 0x80, 0x3F, 0x91, 0x9C, 0x85, 0x65, 0x94, 0x0A, 0x3A, 0xCC, 0x80, 0x89, 0x9E, 0xDB, 0xB4, 0x86, 0xED, 0x52, 0xBF, 0xC1, 0x9D, 0x0E, 0xA3, 0xC5, 0x82, 0x77, 0x5E, 0x29, 0x15, + 0x4E, 0x99, 0xF4, 0x41, 0x89, 0x7F, 0x09, 0x96, 0xAA, 0xC5, 0xC5, 0xCA, 0x5B, 0xBB, 0xF4, 0x97, 0x23, 0x48, 0x32, 0xC8, 0xB5, 0x79, 0x1C, 0xB8, 0xC8, 0xAC, 0xEA, 0x8D, 0xB3, 0xE0, 0x06, 0x50, + }, + .pkcs8_len = 0, + .spki_len = 0, + .msg_len = 66, + .msg = { + 0x22, 0x5D, 0x5C, 0xE2, 0xCE, 0xAC, 0x61, 0x93, 0x0A, 0x07, 0x50, 0x3F, 0xB5, 0x9F, 0x7C, 0x2F, 0x93, 0x6A, 0x3E, 0x07, 0x54, 0x81, 0xDA, 0x3C, 0xA2, 0x99, 0xA8, 0x0F, 0x8C, 0x5D, 0xF9, 0x22, + 0x3A, 0x07, 0x3E, 0x7B, 0x90, 0xE0, 0x2E, 0xBF, 0x98, 0xCA, 0x22, 0x27, 0xEB, 0xA3, 0x8C, 0x1A, 0xB2, 0x56, 0x82, 0x09, 0xE4, 0x6D, 0xBA, 0x96, 0x18, 0x69, 0xC6, 0xF8, 0x39, 0x83, 0xB1, 0x7D, + 0xCD, 0x49, + }, + .sig_len = 4668, + .sig = { + 0x8B, 0xCE, 0xDB, 0xF2, 0xD6, 0x06, 0x90, 0x0B, 0x70, 0xFD, 0xF9, 0x1F, 0x0F, 0x93, 0xE8, 0x36, 0x56, 0x40, 0x89, 0x72, 0xBB, 0x47, 0xE0, 0x17, 0x95, 0x13, 0x74, 0x62, 0x46, 0x38, 0x0C, 0xAE, + 0x70, 0x9A, 0x59, 0x62, 0x2B, 0x9B, 0x23, 0x2D, 0x5B, 0x0D, 0x2D, 0xF5, 0x11, 0x71, 0xCE, 0x64, 0x42, 0x5B, 0x04, 0x38, 0x93, 0x24, 0xA0, 0xA0, 0x03, 0x84, 0x17, 0x00, 0x28, 0x74, 0x50, 0xF7, + 0x5A, 0x81, 0x7B, 0x1C, 0x1D, 0x63, 0xCF, 0xB5, 0x0A, 0xF6, 0x1D, 0x8A, 0xF1, 0x9C, 0xC0, 0xFC, 0xB1, 0xA6, 0x3D, 0x53, 0x72, 0xB8, 0xE7, 0xFF, 0xD0, 0xAF, 0xCB, 0xAC, 0x05, 0xF6, 0x3A, 0xC0, + 0x55, 0xDE, 0x27, 0x8F, 0x46, 0x25, 0x22, 0x34, 0x1C, 0x3E, 0xD6, 0xA1, 0xEE, 0x74, 0x6E, 0x3A, 0xCA, 0x17, 0x4E, 0xA5, 0x1E, 0x0D, 0xCD, 0xEC, 0x02, 0xBB, 0x5C, 0x68, 0x46, 0x88, 0x64, 0x54, + 0x75, 0x90, 0xE0, 0xDE, 0xF0, 0x76, 0x11, 0x1C, 0x3B, 0x45, 0xD1, 0xFA, 0xA7, 0xF3, 0xF3, 0x4C, 0x2E, 0x63, 0x6D, 0x68, 0xB4, 0xF7, 0xD2, 0xBC, 0x04, 0xB7, 0x38, 0x39, 0x59, 0xE0, 0x9E, 0xF7, + 0xB8, 0x4B, 0x04, 0x5C, 0x29, 0xEB, 0xD5, 0x0A, 0xE8, 0x87, 0x42, 0x71, 0xAC, 0x3A, 0x7C, 0xB1, 0xEE, 0x94, 0xC5, 0x53, 0x9A, 0xD0, 0x7E, 0x7E, 0xF9, 0xF6, 0x4D, 0x30, 0x16, 0xDA, 0xF9, 0x66, + 0x1F, 0xEE, 0x09, 0xB9, 0xBF, 0x27, 0xB0, 0xFF, 0x9B, 0xEA, 0x68, 0x90, 0x98, 0x04, 0x13, 0xAC, 0x23, 0x42, 0xC0, 0x9B, 0x4A, 0x65, 0xA8, 0x3B, 0x58, 0x3F, 0x3A, 0x33, 0x23, 0x04, 0x88, 0xCC, + 0x43, 0xAE, 0x30, 0x0D, 0x12, 0xE9, 0xB0, 0x55, 0xC6, 0x5B, 0xD9, 0xC3, 0xA5, 0x1A, 0xA2, 0x7E, 0xF8, 0xBD, 0x04, 0x76, 0x4E, 0x78, 0xDD, 0x8F, 0x1C, 0x62, 0xC6, 0x5C, 0x7F, 0x7E, 0x86, 0x30, + 0xD0, 0xC8, 0x6B, 0xEA, 0x6A, 0x87, 0xFF, 0x8D, 0x2D, 0x6E, 0x16, 0x70, 0x24, 0x8C, 0x89, 0xE1, 0x8E, 0x77, 0x5D, 0xC7, 0x93, 0x1E, 0xC5, 0xAA, 0x3B, 0xAB, 0x0F, 0xFC, 0xC4, 0x49, 0xE1, 0xB2, + 0x0F, 0x42, 0x2C, 0xA4, 0xDD, 0x2F, 0xD2, 0x9B, 0x40, 0x51, 0x0B, 0xB4, 0x1D, 0x63, 0x6B, 0x37, 0x22, 0x2D, 0xE4, 0xA0, 0x85, 0x55, 0xC0, 0x4F, 0xBA, 0x4B, 0x3C, 0x0F, 0x89, 0x7C, 0x99, 0x8A, + 0x2C, 0xE2, 0x16, 0x1B, 0xD1, 0xB3, 0x5D, 0x20, 0xBF, 0x93, 0xA9, 0xD4, 0xFF, 0x8C, 0x28, 0xD2, 0x95, 0xB8, 0x4F, 0x41, 0xF7, 0xF2, 0x74, 0x04, 0x71, 0xF2, 0x76, 0xEE, 0xA4, 0x66, 0xF5, 0xE3, + 0xAC, 0xF8, 0x1B, 0xD5, 0xB6, 0xE9, 0x3B, 0xE4, 0x5F, 0x81, 0x15, 0x85, 0x64, 0xF9, 0x0D, 0x3B, 0xAD, 0x75, 0x52, 0xF5, 0x77, 0x72, 0x51, 0x60, 0xE9, 0x46, 0x7C, 0xBA, 0xEC, 0x5C, 0x8D, 0x86, + 0x2B, 0xEA, 0x9D, 0x83, 0xE1, 0xC1, 0x83, 0x97, 0xC4, 0x1D, 0x68, 0x68, 0x17, 0x74, 0x2E, 0xF5, 0x7E, 0x74, 0x33, 0xC8, 0xEB, 0x9B, 0xA1, 0x56, 0x9B, 0xB7, 0xF4, 0x1A, 0x8E, 0xD8, 0x89, 0xE2, + 0x23, 0xBB, 0xCA, 0x15, 0x3E, 0xBC, 0x02, 0xC0, 0x46, 0x9C, 0x71, 0xD6, 0x63, 0xC4, 0xD2, 0x85, 0x00, 0x8B, 0xF1, 0x85, 0x49, 0x24, 0x3D, 0x0E, 0x46, 0xC8, 0x16, 0xD0, 0xBE, 0x77, 0x50, 0x2C, + 0x79, 0x5C, 0x16, 0x8E, 0x07, 0x53, 0x52, 0xFA, 0x7D, 0xDB, 0xF9, 0xD0, 0xF2, 0xBE, 0xB4, 0x52, 0x8B, 0x48, 0xB5, 0xAB, 0xB2, 0x81, 0x0E, 0x37, 0x7F, 0x53, 0x30, 0xB3, 0xE2, 0xE6, 0x1B, 0xFF, + 0x7B, 0xE9, 0x6B, 0xDC, 0xAB, 0xA5, 0xB5, 0x6B, 0x6C, 0xA5, 0x7C, 0x66, 0x0E, 0x54, 0xE4, 0x49, 0xEC, 0x3B, 0x4C, 0xA2, 0x66, 0x4F, 0xD3, 0xB7, 0xC4, 0xA8, 0x91, 0x97, 0x3E, 0x2A, 0x31, 0xCC, + 0xF8, 0x27, 0x89, 0x2A, 0x1F, 0x75, 0x7F, 0x68, 0x0B, 0x36, 0xF4, 0x0B, 0x08, 0x2C, 0x6A, 0xD5, 0x06, 0x02, 0x1B, 0xAB, 0x7F, 0xE2, 0x2D, 0x46, 0xF6, 0x83, 0x93, 0x34, 0x18, 0x58, 0x67, 0xC0, + 0x16, 0x26, 0xAC, 0x63, 0xA4, 0x16, 0x28, 0x58, 0xA9, 0xDA, 0xC3, 0x25, 0x81, 0x68, 0xDF, 0x61, 0xCB, 0x66, 0xA3, 0xFF, 0x9F, 0xD4, 0x38, 0x76, 0x59, 0x06, 0x19, 0xDB, 0xB3, 0xE5, 0xBE, 0x1E, + 0xBA, 0x5D, 0x67, 0x59, 0x85, 0xE3, 0xBA, 0x6E, 0xC9, 0x84, 0x01, 0x1F, 0x3E, 0x23, 0xCB, 0xFC, 0xDD, 0x7A, 0xB5, 0xE5, 0x50, 0xC6, 0x1A, 0x0B, 0xAA, 0xBA, 0xBC, 0xBF, 0x16, 0xFA, 0xBC, 0x41, + 0x4F, 0xCF, 0x4B, 0xC1, 0x43, 0x4B, 0xAA, 0x03, 0xAE, 0xDD, 0xB8, 0x15, 0x6D, 0xA3, 0x58, 0x71, 0xD4, 0x83, 0xF1, 0x94, 0xAC, 0x3B, 0xF9, 0x18, 0xC9, 0xB7, 0x7B, 0xBA, 0x65, 0x95, 0x97, 0xAD, + 0x5B, 0xA2, 0xB8, 0x95, 0x4E, 0xF4, 0x12, 0x1F, 0xDA, 0xDF, 0x0A, 0xE5, 0xA1, 0x2D, 0x5B, 0xDF, 0x3C, 0xBB, 0xD8, 0xEA, 0x5C, 0x76, 0xBE, 0x81, 0x6E, 0x7E, 0x9A, 0x79, 0x92, 0x70, 0x16, 0x5E, + 0x7E, 0x9F, 0xD7, 0xCB, 0x70, 0x18, 0x80, 0x81, 0x1E, 0xDE, 0x73, 0xF6, 0x12, 0x1E, 0xEC, 0xEE, 0x27, 0x1A, 0xE4, 0xF1, 0x8D, 0xF1, 0x9F, 0x28, 0xA8, 0x10, 0xAB, 0x43, 0x23, 0x2A, 0xA8, 0x40, + 0xF6, 0xDD, 0xCC, 0xB8, 0x6A, 0xE3, 0x96, 0xFE, 0x54, 0xA5, 0x79, 0x77, 0x8F, 0x96, 0xC2, 0xFA, 0x85, 0x70, 0x62, 0x04, 0x7F, 0xF5, 0x3C, 0xA5, 0x42, 0xC4, 0xBA, 0xC1, 0x42, 0x0D, 0x0B, 0x2C, + 0x52, 0xA4, 0x2E, 0xAD, 0xBA, 0xAA, 0x58, 0x5A, 0x44, 0x02, 0x73, 0x17, 0xA7, 0x66, 0x6E, 0x47, 0x4C, 0x55, 0xBF, 0x6F, 0xE0, 0x54, 0xE4, 0x22, 0x92, 0x61, 0x79, 0x88, 0xEE, 0x0A, 0xBF, 0xE2, + 0x28, 0xC7, 0x1B, 0xA4, 0x74, 0x93, 0x26, 0x8C, 0x32, 0x83, 0xBB, 0x62, 0xE4, 0x0A, 0xA0, 0x5D, 0xEF, 0x2C, 0x10, 0xC6, 0x12, 0x1F, 0x76, 0x7F, 0x33, 0xB1, 0x48, 0x9A, 0x1D, 0x20, 0x48, 0x2A, + 0x3D, 0x8D, 0xF8, 0x89, 0x1D, 0xDD, 0x2A, 0x9B, 0xE4, 0xBD, 0x2B, 0x00, 0x73, 0xC5, 0x92, 0x92, 0x34, 0x4A, 0x69, 0x92, 0x79, 0x73, 0x8C, 0xB6, 0xDB, 0x24, 0xA8, 0x97, 0x63, 0x88, 0x7F, 0x2D, + 0x78, 0xE7, 0xE2, 0x6A, 0x04, 0x0E, 0xC2, 0x77, 0x7A, 0xAD, 0xED, 0xCA, 0xE5, 0xB2, 0x62, 0x72, 0xAE, 0x40, 0xCB, 0x65, 0x67, 0xC4, 0x16, 0x72, 0x1D, 0xD4, 0x5C, 0x7B, 0x8F, 0x75, 0x1B, 0x82, + 0x13, 0x11, 0x80, 0xEA, 0x9E, 0x80, 0xEA, 0x97, 0x26, 0x8A, 0x2C, 0x2E, 0x00, 0x9A, 0xD7, 0xBE, 0x1F, 0xDD, 0x4F, 0xD2, 0xA6, 0x17, 0xF7, 0xA8, 0xD7, 0xE2, 0x6B, 0x6D, 0x94, 0x37, 0x30, 0x99, + 0x81, 0xB5, 0x01, 0x3F, 0xC0, 0x72, 0xBE, 0x94, 0xEB, 0x2F, 0x03, 0x6D, 0xD9, 0x0A, 0x78, 0x8D, 0xC5, 0xC1, 0x42, 0xDF, 0x50, 0x5A, 0xCD, 0x26, 0xA0, 0x0D, 0xAF, 0xDC, 0x30, 0xF5, 0x19, 0x0B, + 0x0A, 0x91, 0xBC, 0xBE, 0x49, 0x58, 0x7F, 0x89, 0xB1, 0xD9, 0x99, 0xDE, 0x49, 0x00, 0x9C, 0x0B, 0xD7, 0xEB, 0x95, 0x5E, 0xB3, 0x08, 0x86, 0x73, 0x6B, 0x6D, 0xD4, 0xDC, 0x1D, 0x8D, 0x1D, 0xA6, + 0x80, 0x69, 0x02, 0x39, 0x87, 0x9B, 0x3D, 0x6D, 0xD7, 0x64, 0x72, 0xF3, 0xD6, 0xE3, 0x3B, 0xC8, 0xFD, 0x90, 0xE4, 0x47, 0xE7, 0x0F, 0xD7, 0xE9, 0xF5, 0x0B, 0xF9, 0xA1, 0xA0, 0xAC, 0x9D, 0x88, + 0x32, 0xA4, 0x36, 0xE8, 0x9E, 0x36, 0x44, 0x03, 0x75, 0xF5, 0xDE, 0x88, 0xDC, 0x70, 0xD9, 0x17, 0xCE, 0x13, 0x22, 0x35, 0xB9, 0x1B, 0x20, 0xAE, 0x41, 0x1B, 0x86, 0xC2, 0x19, 0xB5, 0xA3, 0x4D, + 0xB0, 0x29, 0x16, 0x80, 0xE6, 0x15, 0x54, 0xDD, 0x50, 0xF3, 0x26, 0x1F, 0xEA, 0x06, 0xB5, 0xF1, 0x74, 0xEA, 0x6B, 0x13, 0x65, 0x0C, 0x97, 0x9C, 0x5A, 0x72, 0x8F, 0x13, 0xF8, 0xDA, 0x45, 0x57, + 0xEF, 0x8D, 0x9A, 0xF6, 0x41, 0x22, 0x8F, 0xE5, 0xDD, 0x7D, 0x92, 0x28, 0xD7, 0x8C, 0x9A, 0xE8, 0x7E, 0xFE, 0xEA, 0x22, 0x4C, 0x02, 0x12, 0x5E, 0xC2, 0x86, 0xBB, 0x85, 0xC8, 0xB1, 0x2A, 0xCB, + 0x40, 0xF7, 0xEA, 0x12, 0xB0, 0x26, 0xC1, 0xE6, 0x11, 0xEF, 0x99, 0xE0, 0x07, 0x7E, 0xF8, 0x04, 0xD6, 0x56, 0xD0, 0x6B, 0xB4, 0x0C, 0x50, 0xDC, 0xCF, 0xC5, 0x98, 0xC9, 0xD4, 0x04, 0xBF, 0x6B, + 0x56, 0x4F, 0x02, 0xE1, 0x8B, 0x48, 0x2C, 0x7F, 0xB7, 0x4C, 0x68, 0x13, 0xA8, 0xE9, 0x75, 0x8E, 0x6F, 0xCB, 0xF2, 0x28, 0x9C, 0x8F, 0x24, 0x5D, 0xD2, 0x41, 0x67, 0x21, 0x89, 0x9D, 0x7A, 0xD4, + 0xC7, 0x90, 0xD0, 0x0E, 0x47, 0xF5, 0x14, 0x8C, 0xAC, 0x29, 0x0C, 0x66, 0x07, 0x21, 0x6B, 0xD6, 0x6F, 0x2A, 0x6C, 0xA1, 0xC4, 0xE7, 0x6F, 0x9C, 0xC0, 0x15, 0x08, 0x9D, 0x08, 0xF8, 0x39, 0xA0, + 0x95, 0x2F, 0x3B, 0x3C, 0xA8, 0x23, 0x58, 0x16, 0x44, 0xAD, 0x7D, 0xDA, 0x18, 0xC0, 0xBC, 0xC6, 0xE7, 0x46, 0xA7, 0x31, 0xCA, 0xE4, 0x28, 0xCE, 0x7A, 0xD4, 0xCC, 0x81, 0x3B, 0xA9, 0x5D, 0x83, + 0xDC, 0x7D, 0x6E, 0xE0, 0xA3, 0xCD, 0xDC, 0xAB, 0x94, 0x35, 0x00, 0x03, 0x45, 0xC7, 0x1A, 0x09, 0x16, 0x28, 0x2F, 0xD5, 0x3C, 0x4A, 0x86, 0x99, 0xD5, 0x6E, 0x55, 0x20, 0x74, 0x2F, 0x5D, 0xA8, + 0x1C, 0xAA, 0xFA, 0x16, 0x78, 0x26, 0xCF, 0x38, 0x6E, 0xB7, 0x2C, 0xD5, 0x12, 0x6A, 0x59, 0xE2, 0x4F, 0x74, 0x00, 0x9B, 0xB0, 0x45, 0x6C, 0x8D, 0x58, 0x51, 0x9C, 0xD6, 0x7A, 0x9C, 0xE0, 0x9B, + 0xA8, 0x7F, 0x1C, 0xF0, 0x36, 0xEA, 0x9C, 0x7E, 0xDA, 0xD3, 0xBC, 0xD6, 0xDA, 0x32, 0x76, 0x51, 0x8A, 0xFB, 0xB0, 0x4D, 0xF9, 0xA7, 0xE7, 0x73, 0x32, 0x0E, 0xA4, 0x41, 0xA6, 0x2C, 0x64, 0xEA, + 0xEA, 0x8D, 0x42, 0xFC, 0x30, 0x80, 0x4B, 0xFF, 0xEC, 0xC9, 0xBC, 0x2D, 0x2F, 0x46, 0x19, 0x67, 0x56, 0x2D, 0x8D, 0x60, 0x84, 0xC9, 0xFE, 0xD5, 0x21, 0x34, 0xD4, 0xE0, 0x46, 0x90, 0x1E, 0xC0, + 0x31, 0x86, 0x83, 0x32, 0x6D, 0xD0, 0xC8, 0xBE, 0x19, 0xB9, 0xAE, 0x3F, 0x38, 0xFA, 0x2E, 0xE9, 0x46, 0x54, 0x02, 0x98, 0x5E, 0x8E, 0x27, 0x40, 0x67, 0x28, 0x9A, 0x79, 0xEB, 0x55, 0x91, 0x83, + 0x2D, 0x6E, 0xA6, 0x57, 0x8D, 0xF4, 0x77, 0xDF, 0x52, 0xE1, 0x26, 0x45, 0xD1, 0x86, 0x11, 0x24, 0x52, 0x99, 0x0E, 0xA7, 0x53, 0xE4, 0xFF, 0x3F, 0x0C, 0x3D, 0x0A, 0x14, 0x0F, 0xF7, 0x0F, 0x9B, + 0xBE, 0x9A, 0x75, 0x5B, 0xF2, 0x79, 0x50, 0x8A, 0x3C, 0x89, 0x8E, 0x40, 0x85, 0xFC, 0xFC, 0x39, 0x9C, 0x46, 0xC6, 0x82, 0x6D, 0x46, 0xF7, 0xF0, 0x06, 0x3E, 0xA5, 0xA4, 0xC7, 0xE6, 0x6D, 0xC5, + 0x60, 0x8E, 0x37, 0xAF, 0xAF, 0xF8, 0xFC, 0x43, 0xAE, 0x82, 0xC3, 0x36, 0x1C, 0xA8, 0xB2, 0xC6, 0xFB, 0xDE, 0xF1, 0x98, 0xFE, 0xFE, 0x74, 0x50, 0xE4, 0xDA, 0x66, 0x2F, 0x32, 0x42, 0xD5, 0x2C, + 0x0C, 0xE0, 0x2D, 0xBC, 0xAF, 0xF9, 0x44, 0x5A, 0x63, 0x0F, 0x85, 0x74, 0xEA, 0x0E, 0xE0, 0x97, 0x05, 0xC9, 0x1D, 0x39, 0xB8, 0xFA, 0xD7, 0x8C, 0x35, 0xEF, 0xDF, 0x54, 0x7F, 0xB1, 0x01, 0x8C, + 0xDC, 0x89, 0x2A, 0x0C, 0x81, 0x62, 0xFA, 0x7E, 0x07, 0x34, 0xC1, 0xEE, 0x07, 0xFA, 0xD9, 0x47, 0x52, 0x0A, 0xE9, 0x5B, 0x30, 0x22, 0x30, 0x3D, 0xDB, 0x32, 0xF3, 0xD8, 0xDC, 0x4D, 0x68, 0x21, + 0x21, 0x15, 0x13, 0xC6, 0x4E, 0x78, 0x5E, 0x4E, 0xE4, 0x38, 0x5C, 0xD3, 0x75, 0x7D, 0x68, 0x0A, 0xAE, 0xD5, 0x4E, 0x15, 0xFA, 0xE5, 0x27, 0xB4, 0x5A, 0xAE, 0x14, 0xD5, 0x63, 0x82, 0x57, 0x8C, + 0xA2, 0xE1, 0x16, 0xFD, 0x95, 0x4B, 0x56, 0xAC, 0x37, 0x8C, 0x70, 0x44, 0xDA, 0xCC, 0xB8, 0x86, 0xF3, 0x2B, 0xC3, 0xA5, 0x22, 0xBD, 0xEB, 0xEC, 0xBC, 0xAE, 0x5B, 0x77, 0x4B, 0x8E, 0x60, 0x34, + 0xFB, 0xB1, 0x15, 0x6D, 0xE5, 0xC5, 0xF2, 0x16, 0x51, 0x4B, 0xFA, 0x0D, 0x1B, 0x17, 0xD4, 0x73, 0xCD, 0xD2, 0xA0, 0x1D, 0x42, 0x2E, 0xD4, 0x41, 0xAD, 0xC7, 0x17, 0x79, 0x5E, 0x07, 0x82, 0xE4, + 0x43, 0xA2, 0xF7, 0x4B, 0x01, 0x36, 0x53, 0x65, 0x9C, 0xA3, 0x9F, 0x5C, 0x74, 0xC5, 0xDC, 0x98, 0x71, 0x5D, 0x3E, 0xA2, 0x2A, 0x0D, 0x0D, 0xD8, 0x26, 0xCF, 0xB3, 0xBA, 0x7F, 0xB0, 0x09, 0x3B, + 0x9C, 0x80, 0x76, 0x3A, 0x30, 0x8C, 0x22, 0x87, 0x15, 0x3E, 0x21, 0xFB, 0xDE, 0x26, 0xD2, 0xB7, 0x2A, 0x39, 0x32, 0xD7, 0xB5, 0x3B, 0x88, 0xA4, 0xE1, 0xAE, 0xCF, 0x37, 0x49, 0x21, 0xAD, 0x6F, + 0x44, 0x47, 0xA6, 0x31, 0x57, 0xCF, 0x7E, 0x05, 0x8E, 0xF9, 0xBA, 0x1D, 0x72, 0x0B, 0x43, 0xF2, 0x18, 0x0D, 0x2F, 0x55, 0x7F, 0xA2, 0x0E, 0x22, 0xA3, 0xEF, 0x78, 0x5A, 0x08, 0xB5, 0x93, 0x11, + 0x1A, 0xBB, 0x4B, 0x00, 0xDF, 0x39, 0x88, 0x34, 0xC7, 0xE4, 0x80, 0xF0, 0x40, 0x45, 0x3E, 0x9E, 0x92, 0x5C, 0x8D, 0x77, 0x85, 0xD5, 0x98, 0x43, 0x04, 0xB7, 0xE9, 0x9B, 0x20, 0x89, 0x51, 0x9D, + 0x3F, 0x59, 0x14, 0x31, 0x3C, 0xE1, 0x2D, 0x26, 0xE1, 0x90, 0xA4, 0x36, 0xA5, 0x9F, 0x79, 0xB0, 0xB1, 0x25, 0x19, 0x1D, 0x85, 0x43, 0x49, 0x54, 0x78, 0x18, 0x08, 0x16, 0xC9, 0xE6, 0x50, 0x57, + 0x99, 0x32, 0x80, 0x4D, 0xCA, 0x0E, 0x02, 0xE4, 0x69, 0xDD, 0x68, 0x78, 0xFC, 0xE9, 0x2D, 0xFB, 0x49, 0x31, 0xBE, 0xC0, 0xAA, 0x8D, 0x3F, 0x89, 0x7F, 0x2B, 0x9B, 0x91, 0x29, 0xAC, 0x59, 0xF4, + 0x76, 0x51, 0xC1, 0xC8, 0xBE, 0xD8, 0x94, 0x9E, 0xF4, 0x37, 0xA6, 0x74, 0xCB, 0x0D, 0xD1, 0xD2, 0xFC, 0xDB, 0x15, 0x82, 0x14, 0xB6, 0x71, 0xBA, 0xCA, 0x72, 0xDB, 0xD3, 0xBF, 0xCD, 0x34, 0x51, + 0xC9, 0x26, 0x20, 0xDE, 0xE4, 0xDA, 0xC4, 0x06, 0x98, 0x79, 0xE5, 0x0B, 0x3D, 0xD0, 0x22, 0x74, 0xC5, 0x0D, 0x68, 0x37, 0x2E, 0x22, 0x30, 0xAA, 0x56, 0x26, 0xB0, 0x3B, 0x04, 0xBB, 0x4D, 0x2C, + 0xF9, 0x99, 0x97, 0xE0, 0x83, 0x7C, 0xB8, 0xD5, 0xB3, 0x07, 0xCB, 0x35, 0xA1, 0x7D, 0x5A, 0x23, 0xC7, 0xA1, 0x79, 0x76, 0x26, 0x7E, 0xB5, 0x2D, 0x12, 0x31, 0x78, 0xC0, 0x88, 0xFF, 0xE7, 0x2E, + 0x88, 0x4B, 0x38, 0x79, 0xFD, 0x9F, 0xF6, 0x8D, 0xBE, 0xE5, 0x68, 0x7E, 0x89, 0x3F, 0xAA, 0xB7, 0xF4, 0x5A, 0x17, 0xFC, 0x45, 0x59, 0x4B, 0xAF, 0x56, 0x92, 0xAA, 0xDD, 0xF4, 0x3F, 0xC0, 0x4E, + 0xE1, 0x4B, 0x44, 0xE3, 0xA4, 0x6E, 0xA9, 0xEE, 0x53, 0x54, 0x60, 0x49, 0xA3, 0xB1, 0x50, 0x0C, 0x28, 0xEB, 0x86, 0xA7, 0xF4, 0xEF, 0x5F, 0x87, 0x91, 0xF6, 0x44, 0x55, 0x14, 0x14, 0x58, 0x1A, + 0x00, 0x3C, 0x8D, 0x48, 0x49, 0x57, 0xAF, 0x27, 0xC4, 0x7B, 0x65, 0x3B, 0x48, 0xF1, 0xC0, 0xC3, 0x7D, 0xD0, 0x09, 0x99, 0x69, 0xDC, 0x22, 0xF3, 0xB6, 0x6B, 0xB3, 0x91, 0x03, 0xEF, 0xE7, 0x53, + 0xC6, 0xCA, 0x52, 0x8F, 0x64, 0x47, 0x73, 0xDF, 0x5A, 0xCF, 0xCA, 0xE5, 0x53, 0x4D, 0x52, 0x75, 0xDF, 0x3A, 0xF0, 0xAE, 0x87, 0xBF, 0x90, 0x57, 0xD7, 0x15, 0xBA, 0x0E, 0x26, 0xF6, 0xBE, 0x7A, + 0xB9, 0x02, 0xBD, 0xAD, 0xE9, 0x98, 0x3E, 0x1F, 0xE1, 0xA5, 0xBC, 0xF6, 0x7A, 0x21, 0xB3, 0x5D, 0x00, 0xF3, 0x28, 0x48, 0x28, 0x37, 0x99, 0x83, 0x91, 0x3E, 0x86, 0xA1, 0xBF, 0x1E, 0x8F, 0x29, + 0x80, 0xFF, 0x17, 0x48, 0x1E, 0x0B, 0x80, 0x3E, 0x4B, 0xAE, 0xD1, 0x7A, 0x5C, 0x46, 0xB2, 0x61, 0x76, 0xF6, 0x2B, 0xA5, 0x4E, 0x8C, 0x7D, 0xCA, 0x90, 0xD8, 0xA9, 0x82, 0xA9, 0xE6, 0xC6, 0xAC, + 0x70, 0x81, 0x23, 0x4A, 0xC3, 0xF4, 0x01, 0xA4, 0x31, 0x03, 0xA2, 0x17, 0xE4, 0x15, 0xE3, 0x08, 0x83, 0x74, 0x9F, 0x30, 0xA3, 0x97, 0x49, 0x93, 0x40, 0x6D, 0x90, 0xB2, 0x07, 0x22, 0xD5, 0xD1, + 0xB7, 0x26, 0x52, 0xFF, 0x6C, 0x0B, 0x43, 0x2C, 0xA1, 0x90, 0x10, 0xDF, 0x98, 0x4F, 0x78, 0x5D, 0xBB, 0xBE, 0xBE, 0x8B, 0xD6, 0x94, 0x76, 0xD5, 0xCA, 0xAF, 0xE7, 0x10, 0x5A, 0x12, 0x05, 0xCA, + 0x28, 0x41, 0x44, 0x4C, 0x82, 0xF4, 0x4B, 0x3A, 0x1D, 0xC6, 0xAD, 0x47, 0xF9, 0x2C, 0x95, 0x2A, 0x43, 0xBF, 0x25, 0x24, 0xBD, 0x14, 0x93, 0x0E, 0xAF, 0xEA, 0x65, 0xFB, 0xEA, 0x4F, 0x40, 0x28, + 0x98, 0x7C, 0x9D, 0x07, 0x51, 0xC5, 0x5C, 0x4D, 0x63, 0xDE, 0x04, 0x50, 0xF6, 0x26, 0x3A, 0x42, 0x8A, 0xA7, 0x9B, 0xD4, 0xDC, 0xFC, 0x64, 0x7E, 0xDD, 0xC4, 0x13, 0x66, 0x4E, 0xCF, 0x20, 0x72, + 0xCA, 0xB2, 0x1D, 0x57, 0xB2, 0x44, 0x7E, 0xDF, 0xA7, 0x19, 0x4C, 0x4B, 0xCE, 0xDC, 0xAE, 0x28, 0x93, 0xD3, 0xDE, 0x6B, 0xD1, 0xD6, 0xB2, 0xFA, 0xF2, 0x1C, 0xBC, 0x02, 0x12, 0xC6, 0x36, 0xF6, + 0x1B, 0x7A, 0x22, 0x31, 0x28, 0xA3, 0x13, 0xC0, 0x09, 0x9B, 0xF3, 0xAB, 0x1D, 0x28, 0x8A, 0x5C, 0xFD, 0x89, 0x30, 0x25, 0x75, 0x33, 0x1E, 0x00, 0xB6, 0x53, 0xD5, 0x26, 0xB7, 0xB8, 0x74, 0x20, + 0x9B, 0x63, 0x14, 0xFE, 0x15, 0xE7, 0x70, 0x7C, 0x90, 0x9C, 0x97, 0x31, 0xA9, 0xC4, 0xB7, 0xF0, 0xE3, 0xD0, 0x2D, 0xA0, 0x53, 0x1D, 0x22, 0x67, 0xDF, 0xBA, 0x35, 0x5E, 0x85, 0x32, 0x1F, 0x8C, + 0x0C, 0xA9, 0x7A, 0x98, 0x66, 0x66, 0xCA, 0x84, 0xCA, 0xBF, 0x3F, 0xDB, 0xBC, 0x0F, 0xCD, 0x50, 0xB0, 0x60, 0xF8, 0x74, 0x4F, 0x83, 0xD3, 0x93, 0xC1, 0xF9, 0x60, 0x22, 0x1F, 0x14, 0xB3, 0xAF, + 0x44, 0xF3, 0x03, 0x99, 0xB8, 0xA8, 0xF8, 0x34, 0x6C, 0x44, 0x66, 0xA2, 0xBD, 0x4F, 0x01, 0x02, 0x9C, 0x4E, 0x38, 0xA4, 0x54, 0xC9, 0xA9, 0x8D, 0xF2, 0xCD, 0x92, 0xAE, 0x9F, 0x68, 0x6C, 0x1B, + 0x21, 0x62, 0xFE, 0xF3, 0x5F, 0x82, 0xA4, 0xF6, 0x87, 0x68, 0x41, 0x50, 0x31, 0xCD, 0xE2, 0x12, 0x02, 0x78, 0x55, 0x7C, 0x30, 0xAD, 0xFC, 0x51, 0xAA, 0xA6, 0xD9, 0xD6, 0x5D, 0x7B, 0x3B, 0x58, + 0xB1, 0xD1, 0xAF, 0x6B, 0xF1, 0x0B, 0x61, 0x25, 0xAC, 0xDE, 0xB0, 0x53, 0xAA, 0xEE, 0xBC, 0x2A, 0x26, 0x4E, 0x2E, 0x06, 0x55, 0xA3, 0xDE, 0x02, 0x61, 0x13, 0x13, 0x37, 0xF8, 0x42, 0x73, 0x3E, + 0x92, 0x64, 0x4F, 0x0B, 0x38, 0x89, 0x5D, 0xEC, 0xDB, 0xB3, 0xA9, 0x7B, 0x74, 0xDD, 0xCE, 0x55, 0xA3, 0x38, 0x24, 0x8F, 0x74, 0xF8, 0x0B, 0x8A, 0x13, 0x35, 0x1F, 0xD4, 0x33, 0x32, 0xFB, 0x36, + 0xC7, 0xAD, 0xE7, 0xD8, 0x20, 0xD5, 0xE5, 0x50, 0x44, 0xF7, 0x42, 0x31, 0xEE, 0x6A, 0xFF, 0x8A, 0x9D, 0xC2, 0xFC, 0xE0, 0x12, 0xCB, 0x40, 0x69, 0xD0, 0x3D, 0xE1, 0xB7, 0x50, 0x67, 0x15, 0xDD, + 0x36, 0x98, 0x05, 0xC6, 0xCE, 0x3B, 0x16, 0x0C, 0x6C, 0x7D, 0xE3, 0x50, 0x49, 0xC1, 0x65, 0x53, 0x47, 0x98, 0x27, 0x2B, 0x68, 0x0F, 0xA0, 0x20, 0xDD, 0x32, 0x8B, 0xBE, 0xB9, 0x1A, 0x0D, 0x46, + 0x6E, 0x3A, 0x57, 0xFA, 0x2E, 0x66, 0x5D, 0xE4, 0x21, 0x2F, 0xDB, 0x7E, 0xE9, 0x14, 0xA8, 0xB0, 0xD6, 0xFD, 0x5C, 0xE2, 0x03, 0x27, 0x89, 0xE4, 0x8A, 0x35, 0xD0, 0x29, 0x3B, 0x57, 0x42, 0x4C, + 0xAA, 0x60, 0xF4, 0xA6, 0x70, 0x40, 0x7F, 0x48, 0x48, 0xD7, 0xA2, 0x4A, 0x5E, 0xC2, 0xC2, 0x0F, 0x83, 0x96, 0x42, 0x5A, 0x2B, 0x1A, 0xCC, 0x57, 0xB0, 0x8D, 0x96, 0x68, 0xC3, 0x99, 0x16, 0x7B, + 0x46, 0x8E, 0x07, 0x36, 0xB3, 0x3D, 0x46, 0x97, 0xB2, 0x22, 0x55, 0x24, 0x34, 0x82, 0x2A, 0xB6, 0x5B, 0x06, 0x5F, 0x8C, 0x18, 0x57, 0x58, 0xAC, 0xBC, 0x98, 0xA8, 0xB6, 0x47, 0xDA, 0x05, 0x27, + 0x96, 0x61, 0xC4, 0xEF, 0x63, 0xD8, 0xB9, 0x91, 0x2B, 0x0D, 0x29, 0xF3, 0x32, 0x45, 0xD0, 0x5E, 0x8D, 0xFD, 0x79, 0x5C, 0x6C, 0x89, 0x7F, 0x3C, 0xEF, 0xF4, 0x23, 0x8C, 0x1E, 0xFA, 0x1D, 0xEF, + 0xD4, 0xA5, 0x49, 0x98, 0xD4, 0x77, 0x5D, 0x08, 0xA9, 0xD1, 0xF5, 0xE7, 0x11, 0x54, 0x14, 0x6F, 0xCC, 0xE7, 0x59, 0x0B, 0x1F, 0x7E, 0xEE, 0x85, 0x15, 0x55, 0xC0, 0x63, 0xB7, 0xC7, 0xCC, 0xCD, + 0x01, 0xD1, 0x43, 0x3E, 0x07, 0x3E, 0x3E, 0x13, 0xDA, 0x20, 0x44, 0x28, 0x93, 0xDF, 0xBB, 0x37, 0xAF, 0xBA, 0xCD, 0x27, 0x14, 0xEB, 0x43, 0xB4, 0xAD, 0xAC, 0xA2, 0x62, 0x16, 0xF1, 0x4B, 0xFC, + 0xDD, 0x71, 0xCF, 0x0A, 0xA3, 0x43, 0xA6, 0x91, 0xF9, 0x91, 0x69, 0xF3, 0x01, 0x5D, 0x01, 0x96, 0x72, 0x67, 0x84, 0x12, 0x12, 0x8A, 0x71, 0x6F, 0x93, 0xA7, 0x38, 0xD7, 0x20, 0x43, 0x72, 0xF1, + 0x64, 0xD6, 0xC8, 0x05, 0x6D, 0xDF, 0x11, 0x88, 0x8A, 0x3E, 0xFA, 0x15, 0xFE, 0xD6, 0x61, 0x2A, 0x1F, 0xFA, 0xBF, 0x06, 0x81, 0x3F, 0x74, 0x33, 0x04, 0xB9, 0xDD, 0x41, 0xD6, 0x75, 0x2D, 0x43, + 0x3C, 0xAC, 0xA9, 0xE5, 0x42, 0xD1, 0x8B, 0x47, 0x6B, 0x80, 0x4F, 0x73, 0xB9, 0x0A, 0x2A, 0x4E, 0x7B, 0x50, 0x3F, 0xC2, 0xD0, 0x41, 0x8D, 0xC8, 0x19, 0x21, 0x60, 0x10, 0xA8, 0x6E, 0x8F, 0x45, + 0x15, 0x3C, 0xC5, 0xAE, 0xD1, 0xE2, 0x3A, 0xF6, 0x84, 0x89, 0xFA, 0x37, 0x5C, 0x7F, 0x51, 0x81, 0x49, 0xA6, 0xB7, 0x07, 0xCD, 0x6E, 0x52, 0xF6, 0x99, 0xF8, 0x3F, 0x01, 0xEC, 0xFF, 0x69, 0x21, + 0x2B, 0x85, 0x30, 0xC8, 0xBE, 0x5E, 0x25, 0x29, 0x6E, 0x24, 0xE0, 0x98, 0xAB, 0xD9, 0x45, 0x5F, 0x34, 0x0B, 0xD5, 0x75, 0x54, 0x72, 0x5E, 0x23, 0x71, 0x7D, 0x53, 0xA0, 0xA2, 0xC5, 0x0A, 0x84, + 0x78, 0x00, 0xE3, 0x82, 0x29, 0x49, 0xDD, 0x52, 0xC1, 0x70, 0x00, 0x50, 0xE3, 0xB7, 0xE4, 0xE0, 0xF0, 0x84, 0x63, 0xBF, 0x15, 0xAD, 0xC3, 0x21, 0xE9, 0x51, 0xDE, 0xA6, 0x7E, 0x87, 0x04, 0x9B, + 0x98, 0x0D, 0x54, 0x50, 0x33, 0x71, 0x42, 0x89, 0x47, 0x6F, 0xF3, 0x4D, 0x42, 0xD0, 0x61, 0xF8, 0x4A, 0x68, 0x47, 0xFD, 0x5C, 0xA2, 0xC4, 0x4C, 0x3A, 0x3F, 0xDB, 0xEA, 0x68, 0x99, 0x95, 0x7C, + 0xBA, 0x96, 0x0B, 0xA9, 0x12, 0x5A, 0x03, 0x26, 0xA6, 0x04, 0xC2, 0x57, 0xAC, 0xFE, 0xE8, 0x29, 0xD9, 0x66, 0x0D, 0xDE, 0x12, 0x53, 0x9C, 0xD6, 0x72, 0x9D, 0x33, 0xA0, 0x5C, 0x83, 0x57, 0x75, + 0xDD, 0x6C, 0xD7, 0x32, 0x6E, 0x07, 0xD5, 0x2F, 0xE2, 0xDF, 0xED, 0xF6, 0xBB, 0xF9, 0xA8, 0x02, 0x72, 0xC2, 0x5A, 0x90, 0x5A, 0xD9, 0x2B, 0x5D, 0x75, 0x27, 0xD5, 0xA2, 0x22, 0xBA, 0x82, 0xC9, + 0xCD, 0x28, 0xE4, 0xDF, 0xE8, 0x99, 0xAC, 0x17, 0x9F, 0x1F, 0x63, 0xFE, 0x08, 0xA9, 0x86, 0x65, 0x15, 0x41, 0x02, 0xA0, 0xFC, 0xD0, 0xCF, 0xB6, 0x16, 0x62, 0xDB, 0x95, 0x56, 0x52, 0x34, 0xBB, + 0xE1, 0xAB, 0x3A, 0xF9, 0x45, 0xE3, 0x78, 0x23, 0x30, 0xAC, 0x78, 0xD8, 0x4F, 0x8C, 0x85, 0x0B, 0xA3, 0x60, 0xA2, 0xFB, 0xB8, 0x06, 0x2C, 0xB5, 0xBA, 0xA8, 0xCA, 0xF5, 0x0F, 0x8C, 0xF8, 0x04, + 0x24, 0x66, 0x42, 0x0B, 0x4E, 0x56, 0xD5, 0xD1, 0x5C, 0x49, 0xBA, 0xE5, 0x24, 0xA4, 0x5C, 0x04, 0x45, 0x60, 0x64, 0xC2, 0xF4, 0x54, 0x35, 0xDD, 0x1A, 0xBB, 0xA2, 0x49, 0x45, 0x34, 0xE4, 0xD1, + 0xEF, 0xCD, 0x39, 0x8D, 0xE0, 0xC4, 0xA7, 0x77, 0xD1, 0x61, 0xE2, 0x3E, 0xB6, 0xC9, 0x74, 0xED, 0xED, 0xDF, 0x08, 0xF0, 0xA9, 0xC7, 0x58, 0x04, 0xCC, 0xD7, 0x3A, 0x0D, 0xD3, 0x2C, 0xF4, 0x6A, + 0xBD, 0x5F, 0x9E, 0xF1, 0x22, 0x63, 0x27, 0xB7, 0x35, 0x5C, 0xF3, 0x45, 0xAD, 0x09, 0xF8, 0x57, 0xB9, 0x65, 0x3C, 0xDC, 0x1A, 0x4B, 0xF0, 0xF4, 0xC7, 0xAA, 0xC1, 0xF3, 0xDF, 0xB0, 0xA9, 0xE1, + 0x04, 0x8E, 0xBE, 0x0C, 0xBA, 0xB1, 0x72, 0xA3, 0xB0, 0x29, 0x89, 0xCD, 0x6E, 0x63, 0x06, 0x22, 0xE8, 0x74, 0x4C, 0x2F, 0x98, 0x96, 0xB4, 0x40, 0x4D, 0x3A, 0x0B, 0xC2, 0x7C, 0x05, 0x09, 0xE3, + 0xAA, 0x9A, 0x3B, 0x5D, 0x17, 0x1E, 0x91, 0x85, 0x45, 0xAF, 0xB2, 0xE9, 0xC0, 0xB6, 0xEC, 0x5D, 0x3E, 0x50, 0x07, 0x5B, 0x0D, 0x4C, 0x4E, 0x71, 0xD7, 0x8D, 0x85, 0x3E, 0xAE, 0xFA, 0xA5, 0x9B, + 0xED, 0x8C, 0xB9, 0x0D, 0x2B, 0xD6, 0x2A, 0x04, 0x22, 0xB3, 0x6A, 0x88, 0x80, 0x7B, 0x65, 0x21, 0xF4, 0xCB, 0xA0, 0xC3, 0x66, 0x70, 0x5B, 0x11, 0x8E, 0x14, 0x83, 0x1E, 0xD6, 0xCD, 0x78, 0xE3, + 0xB2, 0x72, 0x16, 0xDD, 0xE4, 0x05, 0xAE, 0xEE, 0x96, 0xA0, 0x1A, 0xF1, 0x1D, 0x72, 0x40, 0x03, 0x95, 0x72, 0x7E, 0x7A, 0x93, 0x0C, 0xC7, 0x72, 0x88, 0x18, 0x68, 0xC7, 0xFA, 0xBD, 0x34, 0xF5, + 0xB5, 0x39, 0x2C, 0x76, 0xA0, 0x24, 0x00, 0xDC, 0xCC, 0xEF, 0xED, 0xF2, 0x7B, 0xD9, 0x8C, 0xAD, 0xA7, 0x5E, 0x0E, 0x2E, 0x1E, 0xDE, 0x18, 0x99, 0x29, 0x08, 0xE4, 0x6D, 0x81, 0x93, 0x81, 0x04, + 0xB7, 0xD8, 0xE3, 0x19, 0x13, 0x29, 0x55, 0xA3, 0xC8, 0x0C, 0x93, 0x8E, 0x87, 0x73, 0xD5, 0x93, 0x27, 0x75, 0x99, 0xF8, 0xC9, 0x57, 0xBD, 0x72, 0xE6, 0xC3, 0x3C, 0xF5, 0x2D, 0xEB, 0x84, 0xA1, + 0x36, 0x2D, 0xAC, 0x0A, 0x49, 0xED, 0xE1, 0x80, 0x23, 0x49, 0x5C, 0x50, 0x8C, 0x79, 0x31, 0x93, 0x79, 0xAF, 0xC2, 0xD8, 0x23, 0x2A, 0x8F, 0x6C, 0x19, 0xAD, 0x0E, 0x35, 0x7E, 0xE1, 0xD7, 0x10, + 0x66, 0x48, 0x76, 0xFC, 0x90, 0x2D, 0xB9, 0x3B, 0x1A, 0x0C, 0x1E, 0x25, 0xBB, 0xF1, 0x02, 0x27, 0xC1, 0x53, 0xC6, 0xF9, 0x8C, 0x14, 0xDA, 0xB8, 0x6C, 0x7A, 0x90, 0x53, 0xFC, 0x81, 0xC7, 0x32, + 0xB0, 0x5D, 0x9F, 0x1F, 0x9F, 0x69, 0xB6, 0xE0, 0x86, 0xAB, 0xFF, 0xB8, 0xD9, 0x0D, 0xA2, 0x72, 0xFA, 0x6C, 0x2B, 0x9D, 0x5C, 0x90, 0xFA, 0xCD, 0x34, 0xDD, 0x8F, 0x96, 0xCC, 0x81, 0x60, 0xB6, + 0x8D, 0x5C, 0xB2, 0x7C, 0xCB, 0xD3, 0x5B, 0x48, 0xBF, 0xE6, 0x83, 0xCB, 0x7C, 0x12, 0x6C, 0xF4, 0x97, 0x68, 0x72, 0xAA, 0x46, 0x9D, 0x77, 0xB4, 0x1D, 0x43, 0x23, 0x90, 0x68, 0xDC, 0x37, 0x56, + 0x31, 0x84, 0x17, 0x7E, 0xD5, 0x73, 0xA4, 0x78, 0x3E, 0x0B, 0xB8, 0xCF, 0xE4, 0x50, 0x68, 0x44, 0x6C, 0xCD, 0xBC, 0x39, 0xEA, 0x8A, 0x6D, 0x52, 0x25, 0xF4, 0x69, 0x7C, 0x28, 0x47, 0x21, 0xE8, + 0xEC, 0xA8, 0x26, 0x13, 0x56, 0x87, 0xDC, 0x28, 0x58, 0xE6, 0xCC, 0x73, 0x85, 0xBF, 0xD7, 0x43, 0xA4, 0x62, 0xEC, 0x80, 0xA6, 0x8F, 0x3A, 0xB2, 0xA8, 0xAE, 0x47, 0x32, 0x25, 0x52, 0x15, 0x60, + 0xFB, 0x27, 0x0E, 0xEE, 0xBA, 0x33, 0x4B, 0x4E, 0x48, 0x00, 0x47, 0xDA, 0x1E, 0x40, 0x98, 0xE6, 0x94, 0x7A, 0xB1, 0x2B, 0xE9, 0x53, 0xB3, 0x95, 0x90, 0xFF, 0x82, 0x57, 0x73, 0xC8, 0xCE, 0x23, + 0x18, 0x5E, 0x15, 0x7D, 0xA9, 0x27, 0x13, 0x0E, 0xCD, 0x74, 0x8E, 0x47, 0xB6, 0x2C, 0xA9, 0x80, 0x0A, 0x8D, 0x5F, 0x67, 0x29, 0xCE, 0x3B, 0x8E, 0x94, 0xF5, 0x55, 0xFB, 0xE3, 0x44, 0x6A, 0xA6, + 0xE6, 0xCB, 0x0F, 0xC6, 0xCF, 0xDD, 0xA1, 0x8E, 0x61, 0x7B, 0xBB, 0x86, 0xE0, 0xBE, 0xD6, 0x36, 0xD9, 0x04, 0xAC, 0x41, 0xB2, 0xB2, 0x03, 0x66, 0x3E, 0x44, 0x57, 0x2D, 0x7C, 0x8B, 0x88, 0x4D, + 0x37, 0x4B, 0xA6, 0x65, 0x18, 0x12, 0xB4, 0x62, 0xB5, 0xEF, 0x40, 0xB8, 0xBB, 0x0B, 0xCE, 0xFC, 0x51, 0xEE, 0x4D, 0xE4, 0xC5, 0x73, 0x35, 0xF3, 0xE1, 0xB6, 0x5B, 0xE1, 0x36, 0xF7, 0x18, 0x7C, + 0x34, 0xD7, 0x08, 0xA5, 0xEF, 0x4B, 0xCC, 0x83, 0x3C, 0x6E, 0x57, 0xD7, 0xF6, 0xC2, 0xBD, 0x8C, 0x40, 0x48, 0xA9, 0xC9, 0x97, 0x35, 0xBE, 0x30, 0x13, 0x7C, 0xCB, 0xEF, 0xFE, 0x31, 0x92, 0x4B, + 0x52, 0x06, 0x18, 0xD0, 0x8F, 0x43, 0xE5, 0x6F, 0xB5, 0xAF, 0x1A, 0x5C, 0xDD, 0x81, 0xC4, 0xCF, 0x6F, 0x74, 0x41, 0x8F, 0xA2, 0xB4, 0x22, 0xDA, 0x65, 0x53, 0x3D, 0x8B, 0xF5, 0xF8, 0xE6, 0x42, + 0x4C, 0x55, 0x3C, 0x99, 0x49, 0x45, 0xEE, 0xF2, 0x5F, 0x51, 0x2E, 0x98, 0x26, 0xF7, 0xB0, 0x82, 0xEF, 0xC0, 0x55, 0x48, 0x9A, 0xF4, 0xFC, 0x78, 0x9D, 0x93, 0x6F, 0x6F, 0x9A, 0x7A, 0x53, 0x29, + 0x76, 0x25, 0x87, 0x86, 0xE3, 0xDE, 0x00, 0xF3, 0x4E, 0x75, 0x08, 0xA0, 0x49, 0x51, 0xC8, 0x0D, 0xCA, 0x14, 0xBC, 0xEE, 0x0F, 0x79, 0x42, 0x8D, 0x52, 0xB9, 0xAF, 0x57, 0x84, 0x6D, 0xC9, 0xD4, + 0x85, 0x38, 0xF8, 0xDB, 0x52, 0x60, 0x74, 0x7C, 0xA2, 0x93, 0xBB, 0xFB, 0x2B, 0x43, 0x90, 0xD3, 0x31, 0x73, 0xD9, 0x56, 0x05, 0x37, 0x89, 0x81, 0xD0, 0x39, 0xE2, 0xB4, 0x89, 0xE3, 0xB5, 0xF2, + 0x30, 0xB6, 0xB9, 0x8F, 0x3B, 0x8E, 0x4C, 0x67, 0x26, 0x2B, 0x60, 0xFF, 0xD4, 0x30, 0xEE, 0xFE, 0xB0, 0xB1, 0xCF, 0x43, 0x57, 0xFC, 0x65, 0x8D, 0xA2, 0x3C, 0xC4, 0x82, 0x81, 0x7A, 0x68, 0xAB, + 0x4B, 0x2F, 0xC9, 0x73, 0xA4, 0xE6, 0xE2, 0xDF, 0x59, 0x35, 0x62, 0x24, 0x8F, 0xBD, 0xBA, 0xAD, 0x2F, 0xB5, 0x4B, 0xE0, 0xBE, 0xFA, 0x6E, 0x64, 0x7E, 0x9F, 0x9B, 0x1E, 0x34, 0x7D, 0x1A, 0x61, + 0x4D, 0xE4, 0xC5, 0x87, 0x0C, 0xC9, 0x81, 0x30, 0x9B, 0x87, 0x06, 0xBD, 0xF1, 0xDB, 0x02, 0x8D, 0x04, 0xC0, 0xD5, 0xAD, 0x67, 0xE1, 0x8E, 0x6F, 0x80, 0x6B, 0xE3, 0xD8, 0x61, 0xEB, 0xA9, 0x72, + 0x08, 0xDC, 0xAA, 0xF9, 0x32, 0xC9, 0x79, 0xBC, 0xA1, 0xA6, 0xD1, 0xC9, 0x8C, 0x8A, 0xE4, 0x4E, 0xE7, 0xE3, 0xF8, 0x22, 0xBD, 0x31, 0x7D, 0xEB, 0x6B, 0xB3, 0x7A, 0xCF, 0x83, 0x19, 0x29, 0x14, + 0x83, 0xD5, 0x1D, 0x74, 0xE0, 0xA9, 0x95, 0x30, 0xEE, 0xC7, 0xBB, 0x30, 0x21, 0x62, 0x88, 0xB2, 0x8F, 0x89, 0x19, 0x64, 0x0C, 0xA6, 0x71, 0x8A, 0x6F, 0x81, 0x89, 0xCF, 0xAC, 0x6D, 0xD9, 0x0A, + 0x4A, 0xF3, 0xC0, 0xCE, 0x07, 0x08, 0x63, 0x71, 0xF8, 0xCC, 0x98, 0x0F, 0xC2, 0xA7, 0x0B, 0x2B, 0xF6, 0x4B, 0xA4, 0xC6, 0xE2, 0xE4, 0xC3, 0x5A, 0x46, 0xBE, 0x9E, 0xCC, 0x75, 0x1A, 0xFB, 0x11, + 0x7D, 0x98, 0x35, 0xA7, 0xB8, 0x27, 0xFD, 0x04, 0xEE, 0xF4, 0x4E, 0x5A, 0xEF, 0x2F, 0xE8, 0xFA, 0xD6, 0x70, 0xA9, 0x6C, 0xEE, 0x19, 0x97, 0x21, 0x22, 0x77, 0xAC, 0x1A, 0x5F, 0x45, 0x51, 0xA3, + 0x23, 0x62, 0xC1, 0xB2, 0xF7, 0xC5, 0x43, 0x7B, 0x5F, 0x2E, 0x21, 0xA8, 0xD8, 0xEA, 0x30, 0x8C, 0x7D, 0xF5, 0x75, 0x4D, 0x48, 0xCF, 0x0B, 0xB2, 0xC4, 0x64, 0x6C, 0x51, 0x2E, 0x50, 0x44, 0x07, + 0x5E, 0xD3, 0x85, 0x2B, 0x13, 0x16, 0xDD, 0xE1, 0x54, 0x90, 0x55, 0x54, 0x74, 0x77, 0x3F, 0x9D, 0x62, 0xB3, 0xC5, 0xCC, 0xCC, 0xBE, 0x51, 0x35, 0xB5, 0x31, 0x47, 0x2D, 0xA5, 0xF2, 0x5E, 0x64, + 0x7D, 0x84, 0xE0, 0xD2, 0x19, 0x3A, 0xF3, 0x69, 0x3F, 0xEB, 0x10, 0xE9, 0xBA, 0xE8, 0x22, 0x3B, 0x5F, 0x4A, 0xE3, 0x53, 0x60, 0x18, 0x1E, 0xCB, 0x84, 0xF6, 0xE7, 0x90, 0x98, 0x35, 0x8F, 0xD5, + 0x4D, 0x28, 0x39, 0x75, 0x2F, 0xBC, 0x34, 0x04, 0x8B, 0xC4, 0x3C, 0x1F, 0xE9, 0xC0, 0xB4, 0xD9, 0x9A, 0x36, 0x47, 0x09, 0xA6, 0x8C, 0x1E, 0x1E, 0x9D, 0xBE, 0x00, 0x8A, 0x2F, 0x49, 0x13, 0x61, + 0x7B, 0x41, 0x6B, 0x13, 0x87, 0xE9, 0x3C, 0x9A, 0xA8, 0xAA, 0x63, 0x3B, 0x9C, 0x3E, 0xD6, 0xC7, 0x6A, 0xB5, 0xB0, 0xD3, 0x06, 0xAD, 0x73, 0x65, 0x92, 0xF6, 0x7C, 0xD1, 0x84, 0x65, 0x4D, 0x89, + 0x41, 0x85, 0x5A, 0x02, 0x85, 0xD0, 0xEE, 0xF2, 0x97, 0x8C, 0xC5, 0xD6, 0xA3, 0x04, 0x5A, 0x2C, 0xEB, 0x4D, 0x5C, 0xEE, 0xCF, 0xC9, 0x13, 0x38, 0xD5, 0xB9, 0x18, 0x0B, 0x0B, 0xE7, 0xCE, 0xBC, + 0x82, 0xFA, 0x0C, 0xAA, 0x28, 0x31, 0x90, 0x2A, 0x5B, 0x36, 0x58, 0x89, 0x64, 0x65, 0x28, 0x23, 0xD2, 0x5C, 0xB2, 0xC8, 0x1C, 0x3C, 0xBF, 0xFB, 0xB6, 0x91, 0x70, 0xD6, 0x67, 0xF5, 0xE5, 0x24, + 0xC6, 0xED, 0xCD, 0x0C, 0x09, 0x91, 0x85, 0xE9, 0xC1, 0xCB, 0xFF, 0x57, 0xF8, 0x75, 0x56, 0x0C, 0xBD, 0xD4, 0x68, 0xE7, 0x78, 0xD9, 0x37, 0x2B, 0xDC, 0x61, 0xC1, 0xAD, 0xD1, 0x53, 0x21, 0xBD, + 0xA9, 0xCC, 0xF4, 0xAF, 0xD4, 0xE1, 0xCE, 0x80, 0x10, 0x06, 0xC1, 0xED, 0xE8, 0x0E, 0xA2, 0xE2, 0x11, 0xBE, 0x68, 0x24, 0x62, 0xBC, 0xFA, 0x72, 0xDA, 0x1B, 0x58, 0x3C, 0xD7, 0x57, 0xD5, 0xC7, + 0x38, 0xA7, 0x5E, 0x07, 0xC9, 0x00, 0xDB, 0x5C, 0xEE, 0xFF, 0xDF, 0xF2, 0x95, 0xD0, 0xD5, 0xA8, 0x1C, 0x46, 0x0D, 0x8B, 0xB5, 0x50, 0x9A, 0x06, 0x9D, 0x50, 0x43, 0x84, 0x2A, 0x48, 0x33, 0xDA, + 0x80, 0xE1, 0x4A, 0xC7, 0xAB, 0xBD, 0x5B, 0xE2, 0x48, 0xFC, 0x1E, 0x4D, 0x96, 0x8E, 0xE3, 0x8E, 0x48, 0xCE, 0xFA, 0x79, 0x05, 0x20, 0xA7, 0x40, 0x72, 0x93, 0x33, 0xF4, 0x33, 0xDA, 0xC9, 0x28, + 0x38, 0x0C, 0xDF, 0x83, 0x11, 0x32, 0x80, 0x71, 0xFA, 0x95, 0x75, 0x7F, 0xA6, 0x2A, 0x93, 0x55, 0x1A, 0x58, 0x06, 0x2D, 0x14, 0x27, 0x09, 0x1A, 0x59, 0x20, 0xF7, 0x57, 0x6E, 0x2F, 0x4D, 0x6B, + 0x07, 0x0B, 0x0E, 0x16, 0x3A, 0x4E, 0x58, 0x70, 0x88, 0x97, 0x9B, 0xB6, 0xC4, 0xDA, 0xDD, 0xFC, 0x09, 0x0E, 0x24, 0x27, 0x2B, 0x3B, 0x52, 0x57, 0x5E, 0x63, 0x66, 0x71, 0x7F, 0xA0, 0xF0, 0x07, + 0x16, 0x37, 0x43, 0x4A, 0x4C, 0x6F, 0x78, 0x7C, 0xAC, 0xB4, 0xBF, 0xC7, 0xE4, 0xFA, 0x17, 0x2F, 0x4C, 0x83, 0x87, 0xAA, 0xB7, 0xD0, 0xF5, 0x02, 0x35, 0x3E, 0x56, 0x5F, 0x6A, 0x89, 0x91, 0xB2, + 0xC2, 0xC5, 0xCF, 0xDF, 0xEE, 0x1F, 0x31, 0x52, 0x5B, 0x90, 0xA8, 0xB9, 0xC6, 0xE0, 0xEB, 0xED, 0x03, 0x45, 0x56, 0x5E, 0x6D, 0x70, 0x8F, 0x97, 0xD0, 0xD7, 0xDE, 0x04, 0x11, 0x2D, 0x30, 0x47, + 0x71, 0x72, 0x8F, 0x97, 0xAE, 0xB1, 0xB6, 0xC2, 0xC8, 0xE1, 0xE4, 0xE7, 0xF1, 0xFB, 0xFC, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x1F, 0x2E, 0x37, 0x45, 0x50, 0x5B, 0x6F, 0x00, 0x85, 0x0C, 0x10, 0x38, 0x0E, 0x88, 0x00, 0xB4, 0x00, 0x61, 0x84, + 0x02, 0x26, 0x00, 0x02, 0x90, 0x80, 0x0E, 0x88, 0x88, 0x63, 0x82, 0x0B, 0x00, 0x02, 0x04, 0x21, 0x80, 0x18, 0x33, 0x60, 0x7D, 0xAE, 0xCB, 0x4F, 0xC3, 0xB6, 0xD6, 0x0E, + }, + }, + { + .name = "Dilithium Round 3, Level 3 (4-4) KAT 0 (PKCS#8/SPKI)", + .version = 0, + .keyform = 0, + .rho_len = 0, + .seed_len = 0, + .tr_len = 0, + .s1_len = 0, + .s2_len = 0, + .t0_len = 0, + .t1_len = 0, + .pkcs8_len = 3876, + .pkcs8 = { + 0x30, 0x82, 0x0F, 0x20, 0x02, 0x01, 0x00, 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0B, 0x07, 0x04, 0x04, 0x05, 0x00, 0x04, 0x82, 0x0F, 0x08, 0x30, 0x82, 0x0F, 0x04, + 0x02, 0x01, 0x00, 0x03, 0x21, 0x00, 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, + 0x38, 0xD5, 0x06, 0xD8, 0x5B, 0xEF, 0x03, 0x21, 0x00, 0x39, 0x4D, 0x16, 0x95, 0x05, 0x9D, 0xFF, 0x40, 0xAE, 0x25, 0x6C, 0x5D, 0x5E, 0xDA, 0xBF, 0xB6, 0x9F, 0x5F, 0x40, 0xF3, 0x7A, 0x58, 0x8F, + 0x50, 0x53, 0x2C, 0xA4, 0x08, 0xA8, 0x16, 0x8A, 0xB1, 0x03, 0x21, 0x00, 0x87, 0xD0, 0xAD, 0x11, 0x52, 0x21, 0x10, 0x93, 0x14, 0x94, 0xBF, 0x2C, 0xAE, 0xAE, 0x36, 0x97, 0x97, 0x11, 0xBC, 0x58, + 0x5B, 0x32, 0xF0, 0x8C, 0x78, 0x49, 0x6F, 0x37, 0x9D, 0x60, 0x4D, 0x53, 0x03, 0x82, 0x01, 0x81, 0x00, 0xC0, 0xA6, 0x71, 0x1A, 0x96, 0x6C, 0x11, 0x31, 0x2A, 0xD9, 0xA8, 0x21, 0xD8, 0x08, 0x65, + 0x42, 0xA6, 0x00, 0xA4, 0xB4, 0x2C, 0x19, 0x40, 0x72, 0x02, 0x42, 0x62, 0x81, 0x06, 0x21, 0x0A, 0x43, 0x85, 0x23, 0x31, 0x70, 0x93, 0x08, 0x10, 0x8B, 0x18, 0x8C, 0x02, 0x24, 0x92, 0xC1, 0xB2, + 0x84, 0x12, 0xC4, 0x21, 0x8B, 0x04, 0x21, 0x81, 0xC8, 0x61, 0x02, 0x48, 0x05, 0x9C, 0x92, 0x01, 0xC0, 0x34, 0x88, 0x19, 0x32, 0x6C, 0x58, 0x20, 0x46, 0x89, 0x18, 0x68, 0xA2, 0xC2, 0x8D, 0x82, + 0x34, 0x6A, 0x1C, 0x09, 0x42, 0x00, 0xA2, 0x8C, 0xE3, 0xA6, 0x49, 0x1C, 0x11, 0x2C, 0xC2, 0x48, 0x12, 0xE0, 0x90, 0x21, 0x91, 0x98, 0x50, 0x62, 0xC0, 0x84, 0x62, 0x24, 0x51, 0xCA, 0x06, 0x2C, + 0x64, 0x24, 0x0E, 0x1B, 0xB3, 0x31, 0x24, 0x96, 0x85, 0x4B, 0x46, 0x06, 0xDB, 0x26, 0x68, 0xC3, 0x82, 0x68, 0x44, 0x10, 0x46, 0xC9, 0xB6, 0x21, 0x14, 0x04, 0x81, 0x14, 0x45, 0x50, 0x24, 0x42, + 0x08, 0x44, 0x22, 0x71, 0x0B, 0x92, 0x45, 0x9A, 0xA0, 0x81, 0x1A, 0x91, 0x70, 0x9C, 0x24, 0x10, 0x03, 0x95, 0x70, 0x04, 0xC5, 0x04, 0xC8, 0x26, 0x92, 0xD2, 0x92, 0x00, 0xC0, 0xB2, 0x60, 0xC0, + 0xA2, 0x68, 0x09, 0x19, 0x0A, 0xA2, 0x30, 0x0E, 0x18, 0x89, 0x69, 0xE0, 0x00, 0x8D, 0xD8, 0x48, 0x62, 0xDA, 0x14, 0x71, 0x20, 0x18, 0x05, 0x19, 0x07, 0x44, 0x04, 0x12, 0x40, 0x9B, 0x12, 0x40, + 0x11, 0x80, 0x10, 0xD1, 0x42, 0x81, 0x99, 0x28, 0x50, 0x8B, 0x10, 0x91, 0x02, 0x24, 0x64, 0xA0, 0x20, 0x6D, 0x12, 0x46, 0x21, 0x1C, 0x83, 0x8C, 0x1B, 0x47, 0x69, 0x01, 0x06, 0x90, 0xCC, 0x06, + 0x24, 0x81, 0x84, 0x69, 0x20, 0x98, 0x2C, 0x24, 0x12, 0x05, 0x21, 0xB1, 0x50, 0x41, 0x36, 0x02, 0x98, 0x44, 0x6E, 0xD1, 0xA6, 0x31, 0x11, 0x05, 0x6A, 0xD3, 0xA8, 0x40, 0xCA, 0xA8, 0x4C, 0x62, + 0xB0, 0x00, 0x03, 0x13, 0x4A, 0x53, 0x34, 0x46, 0x14, 0x19, 0x40, 0x04, 0xC5, 0x4C, 0xE3, 0x06, 0x69, 0x5A, 0xB0, 0x89, 0x61, 0x16, 0x8E, 0xCB, 0x10, 0x80, 0x8B, 0x16, 0x8E, 0xD9, 0x90, 0x64, + 0x0B, 0x94, 0x60, 0x24, 0x83, 0x85, 0x1A, 0xB3, 0x04, 0x54, 0x26, 0x22, 0x51, 0xB8, 0x25, 0x1C, 0x42, 0x4A, 0x0B, 0x81, 0x48, 0x42, 0xC4, 0x44, 0x5A, 0x10, 0x20, 0x23, 0x80, 0x84, 0x09, 0xB7, + 0x25, 0x4C, 0xC6, 0x48, 0x14, 0x85, 0x4D, 0x19, 0x38, 0x0E, 0x60, 0x16, 0x51, 0xD8, 0x32, 0x6A, 0x0A, 0x91, 0x89, 0x08, 0xC1, 0x70, 0xE0, 0x96, 0x4D, 0x18, 0x46, 0x8C, 0x01, 0x32, 0x8D, 0x91, + 0xC4, 0x05, 0x4A, 0x00, 0x61, 0x23, 0x08, 0x68, 0xA2, 0x10, 0x42, 0x10, 0xA8, 0x61, 0x13, 0x06, 0x21, 0x03, 0x82, 0x01, 0x81, 0x00, 0x8A, 0x24, 0x8E, 0x62, 0x06, 0x89, 0xC9, 0xB2, 0x45, 0x08, + 0x27, 0x84, 0x51, 0x20, 0x0D, 0x98, 0x04, 0x66, 0xDC, 0x42, 0x05, 0x44, 0x24, 0x85, 0x24, 0x26, 0x28, 0x22, 0x21, 0x61, 0x20, 0x16, 0x09, 0x0B, 0xA6, 0x2C, 0x0A, 0x11, 0x44, 0xE0, 0x92, 0x81, + 0x58, 0x48, 0x0D, 0x42, 0x22, 0x10, 0xA0, 0x06, 0x09, 0x8B, 0x24, 0x6E, 0x81, 0x28, 0x8C, 0xC0, 0x24, 0x80, 0x90, 0x30, 0x8D, 0x84, 0x36, 0x40, 0x4C, 0xA6, 0x84, 0x50, 0x04, 0x24, 0x94, 0xB6, + 0x8D, 0xA2, 0x92, 0x6D, 0x18, 0xB3, 0x44, 0xA0, 0x00, 0x85, 0xE3, 0xB8, 0x05, 0x14, 0x05, 0x04, 0xA4, 0xC2, 0x90, 0x84, 0x22, 0x81, 0xC3, 0x26, 0x2D, 0x0B, 0x20, 0x66, 0xCC, 0x90, 0x31, 0x98, + 0x38, 0x28, 0x10, 0x16, 0x6C, 0xC1, 0x34, 0x45, 0xC0, 0x10, 0x22, 0x24, 0xC6, 0x88, 0x03, 0x46, 0x32, 0xD8, 0x40, 0x90, 0x1C, 0x20, 0x68, 0x04, 0x15, 0x28, 0x9A, 0x18, 0x81, 0x44, 0x98, 0x8D, + 0x9C, 0x20, 0x6E, 0x9C, 0x30, 0x2C, 0xC1, 0xB8, 0x20, 0x61, 0x42, 0x21, 0x08, 0x03, 0x10, 0xA0, 0xC2, 0x8C, 0x58, 0x12, 0x85, 0x53, 0x20, 0x4C, 0x03, 0x30, 0x81, 0x4C, 0xA4, 0x8D, 0x44, 0xC0, + 0x8D, 0x51, 0x40, 0x4C, 0x1C, 0xA7, 0x2C, 0x44, 0x08, 0x65, 0xA0, 0x38, 0x40, 0xDA, 0x20, 0x80, 0x81, 0x06, 0x85, 0x8C, 0x26, 0x0D, 0xE2, 0xA8, 0x8C, 0x9C, 0x44, 0x11, 0x59, 0x42, 0x28, 0xC4, + 0x26, 0x04, 0x44, 0x14, 0x26, 0xA1, 0x42, 0x64, 0x08, 0xC0, 0x85, 0x11, 0x01, 0x86, 0x9B, 0x48, 0x31, 0x99, 0xB2, 0x0C, 0x80, 0x46, 0x44, 0x59, 0xA8, 0x8C, 0x00, 0x42, 0x08, 0x98, 0x82, 0x90, + 0x0A, 0xB5, 0x45, 0x62, 0x24, 0x48, 0x12, 0x96, 0x05, 0x44, 0x12, 0x46, 0x00, 0xC8, 0x88, 0x13, 0xA0, 0x61, 0xE1, 0x28, 0x4D, 0x0A, 0xB9, 0x91, 0x4B, 0x96, 0x20, 0x99, 0xB8, 0x44, 0x00, 0x31, + 0x4E, 0x98, 0x12, 0x85, 0x00, 0xB6, 0x01, 0x83, 0xA0, 0x0D, 0x14, 0x15, 0x0E, 0x18, 0x81, 0x10, 0x19, 0x01, 0x22, 0x4A, 0x06, 0x68, 0x1A, 0x49, 0x8D, 0xE1, 0xA2, 0x84, 0x11, 0xC6, 0x31, 0x21, + 0x26, 0x25, 0x91, 0xA0, 0x6D, 0x03, 0x05, 0x24, 0xA1, 0xB6, 0x08, 0x94, 0x44, 0x72, 0x43, 0x34, 0x12, 0x5B, 0xB4, 0x20, 0x41, 0xB6, 0x50, 0xD0, 0x88, 0x8D, 0x0B, 0x07, 0x4D, 0x1C, 0x94, 0x64, + 0x4C, 0x20, 0x8E, 0x8B, 0x88, 0x08, 0xE0, 0x30, 0x09, 0x44, 0x20, 0x05, 0x49, 0x86, 0x4D, 0x03, 0x13, 0x4E, 0x19, 0xC9, 0x84, 0x09, 0x37, 0x61, 0x1A, 0x43, 0x68, 0x4A, 0x80, 0x90, 0x02, 0x04, + 0x31, 0x1C, 0x17, 0x42, 0x18, 0x40, 0x80, 0xC8, 0x30, 0x8E, 0xE1, 0xA2, 0x41, 0xC3, 0x34, 0x04, 0xA3, 0x28, 0x22, 0x51, 0x24, 0x71, 0x03, 0x82, 0x06, 0x81, 0x00, 0x88, 0xD6, 0xFE, 0xF4, 0x67, + 0x12, 0xCA, 0x18, 0x28, 0x72, 0xAB, 0x29, 0x19, 0x67, 0x8A, 0xFF, 0x9D, 0x94, 0xE7, 0x43, 0xE0, 0x63, 0xA3, 0x9E, 0x0C, 0x35, 0xCA, 0xF7, 0x2A, 0x7F, 0x2E, 0xDA, 0x28, 0xE6, 0x58, 0x58, 0x52, + 0x0D, 0x5D, 0x84, 0x67, 0xDE, 0x74, 0x7C, 0xF3, 0x40, 0x65, 0x3B, 0x52, 0xC2, 0x68, 0xF5, 0x54, 0x13, 0xF5, 0xAD, 0xDC, 0x7D, 0x49, 0x01, 0x1E, 0xC3, 0x3E, 0xDD, 0x53, 0x74, 0x23, 0xA8, 0x42, + 0x88, 0x86, 0x93, 0x37, 0xAE, 0xA0, 0x78, 0x1A, 0x12, 0x42, 0x69, 0x07, 0x14, 0x51, 0x72, 0x2D, 0xB3, 0xBB, 0x8F, 0x2C, 0xE5, 0xB1, 0x55, 0x2F, 0x83, 0xD2, 0xAF, 0x07, 0xF2, 0x56, 0x13, 0x91, + 0x8A, 0x9F, 0x4E, 0x6F, 0x12, 0x57, 0x60, 0x38, 0x88, 0xE5, 0x89, 0x30, 0x8C, 0xA5, 0xF9, 0x5F, 0x07, 0x14, 0x3D, 0x23, 0xBA, 0xAE, 0x17, 0x52, 0x0B, 0x36, 0xB6, 0xE0, 0xE9, 0x4F, 0xAF, 0x68, + 0x45, 0xEB, 0x21, 0x31, 0xAE, 0xC3, 0x83, 0xE6, 0x3B, 0xC8, 0x64, 0x4E, 0xE5, 0xF1, 0xAC, 0xCB, 0xA8, 0x2F, 0x92, 0x11, 0xE5, 0x7A, 0xFC, 0xBF, 0x50, 0x9C, 0x11, 0x31, 0xA3, 0x74, 0x66, 0xBC, + 0x91, 0xB3, 0x57, 0xDC, 0xBB, 0xBC, 0x14, 0xCC, 0xC3, 0x19, 0xC4, 0xCC, 0x6A, 0xC7, 0x5F, 0xCD, 0xC8, 0x2C, 0x65, 0x96, 0xD0, 0x77, 0x70, 0xC8, 0x27, 0x7A, 0xD3, 0x70, 0xB1, 0x92, 0xA0, 0xB4, + 0xE0, 0x5F, 0x81, 0x2E, 0x0E, 0x26, 0x5D, 0x29, 0x12, 0xAA, 0x29, 0xF0, 0x3F, 0xC9, 0xF7, 0x2D, 0xFA, 0x69, 0xC9, 0xB1, 0x29, 0x1A, 0x3F, 0xC5, 0x83, 0x64, 0x2B, 0x23, 0x5F, 0x69, 0x91, 0xA9, + 0x54, 0x78, 0x83, 0x47, 0xF6, 0x0A, 0x03, 0x28, 0xC4, 0x8E, 0xCE, 0xE5, 0x1B, 0xA0, 0x2D, 0xFF, 0x32, 0x3A, 0xBD, 0x91, 0x16, 0x67, 0xCB, 0x14, 0x54, 0x9B, 0x61, 0x8F, 0x1C, 0x5D, 0x25, 0x0C, + 0xAC, 0x9E, 0x35, 0xE0, 0x71, 0x60, 0x19, 0x92, 0xFB, 0xEC, 0x0B, 0xAE, 0x6F, 0x74, 0x21, 0x30, 0x81, 0x40, 0x47, 0x44, 0xD1, 0x2F, 0x2A, 0x0E, 0x04, 0xBD, 0xB2, 0x65, 0xE0, 0x92, 0x4C, 0xAD, + 0xA4, 0x0D, 0x1F, 0xA1, 0xF3, 0x8A, 0xCA, 0x46, 0x06, 0xBF, 0xD4, 0x57, 0x57, 0x12, 0xB8, 0x26, 0x0A, 0x45, 0x6F, 0xDD, 0xEE, 0xEF, 0xE7, 0xCA, 0x25, 0x9B, 0xCD, 0xA9, 0x7B, 0x9B, 0x93, 0x9A, + 0x5F, 0xD2, 0x88, 0x9C, 0x9B, 0x49, 0xFB, 0x7D, 0x4E, 0x35, 0x53, 0xDE, 0xA6, 0x1B, 0x33, 0x39, 0xBD, 0x0E, 0x6B, 0x16, 0xBF, 0x3B, 0xB2, 0x27, 0x10, 0x3B, 0xF9, 0x20, 0x2E, 0x72, 0xDC, 0x50, + 0x2E, 0x28, 0xF7, 0xCE, 0x15, 0x59, 0xA4, 0x63, 0x1F, 0x37, 0x25, 0x20, 0x32, 0x4E, 0x4E, 0xBA, 0x07, 0x54, 0x5F, 0x78, 0xBF, 0x4D, 0x94, 0xB0, 0xE5, 0xB8, 0xBF, 0x51, 0xB8, 0xF1, 0x76, 0x53, + 0x3D, 0x5C, 0xFE, 0xA5, 0x23, 0x2F, 0x28, 0x3A, 0x47, 0x60, 0x5F, 0xA6, 0x5D, 0xDB, 0x17, 0xC8, 0x91, 0xC2, 0x51, 0x01, 0x1C, 0x4E, 0x98, 0xEE, 0xB6, 0xEB, 0x00, 0xCB, 0x65, 0xBA, 0x31, 0xC8, + 0xF0, 0x25, 0xC8, 0x7A, 0x9F, 0xE0, 0x2D, 0xBC, 0x10, 0xC5, 0xD8, 0x3A, 0x06, 0x5E, 0xBA, 0x5D, 0x7B, 0x2A, 0x19, 0xD5, 0xA1, 0xCB, 0x2C, 0x16, 0x0A, 0xE1, 0x66, 0xE8, 0x67, 0xF2, 0xAF, 0x8C, + 0x7D, 0x49, 0xD6, 0x3F, 0xB8, 0x3A, 0x61, 0x49, 0x57, 0xFC, 0x0A, 0x3B, 0x5A, 0x5C, 0x74, 0x99, 0x0E, 0x9A, 0x2B, 0x02, 0x12, 0x0C, 0x7E, 0x6D, 0xE3, 0x7E, 0x15, 0x5F, 0xB4, 0x72, 0xF5, 0x0F, + 0x0A, 0x45, 0xE4, 0x7C, 0xF5, 0xF9, 0xD7, 0xA4, 0xC8, 0x29, 0x82, 0xC9, 0xDC, 0x86, 0xAE, 0x87, 0x7C, 0x3F, 0xD1, 0x88, 0x59, 0x43, 0xE4, 0x39, 0xFB, 0x00, 0x3C, 0x7A, 0x9A, 0x42, 0xF7, 0x1B, + 0x4F, 0xF6, 0xF0, 0xA2, 0x8B, 0x14, 0x0C, 0xBD, 0xBA, 0x6E, 0x71, 0xB1, 0x3A, 0xC3, 0x1B, 0x23, 0xDE, 0x9E, 0xAB, 0x78, 0x37, 0xE1, 0x5A, 0x69, 0xF8, 0x33, 0xEB, 0x7B, 0x56, 0xA7, 0x1D, 0x8B, + 0xC2, 0xCA, 0xF1, 0xF2, 0xA3, 0x1C, 0x34, 0x5B, 0xD5, 0xF4, 0x6E, 0xE0, 0x13, 0xA7, 0xC6, 0x89, 0x37, 0x23, 0x37, 0x19, 0x1D, 0xAA, 0x80, 0x0C, 0x0A, 0xC6, 0xC4, 0x6C, 0x9F, 0xF6, 0x88, 0xB1, + 0xA0, 0x13, 0x47, 0xF2, 0x57, 0xC4, 0x74, 0xAA, 0x3D, 0x97, 0xC1, 0xD6, 0x3A, 0x8C, 0x00, 0xE0, 0xA3, 0x7B, 0x68, 0x16, 0x73, 0xF5, 0x7C, 0x1C, 0x9C, 0x8F, 0xCC, 0xD4, 0x6F, 0x17, 0x4C, 0x74, + 0xA2, 0x9D, 0x84, 0xCE, 0xB7, 0x1F, 0x7E, 0x6B, 0x2F, 0x8C, 0xD2, 0xB0, 0x89, 0xED, 0x43, 0xF7, 0xC9, 0x6D, 0xAE, 0x81, 0xA2, 0x23, 0x41, 0x8C, 0x20, 0xB1, 0x6F, 0x1D, 0xF3, 0xD1, 0xA9, 0x78, + 0xAE, 0x28, 0xF6, 0xDF, 0x35, 0xEC, 0x55, 0x9D, 0x04, 0xD2, 0x0E, 0xC7, 0x4B, 0x22, 0x4A, 0xEA, 0x31, 0xA2, 0x89, 0xB0, 0x15, 0xB0, 0x69, 0xE9, 0xCB, 0xBB, 0xF7, 0xCF, 0x6D, 0xE9, 0x4C, 0xFB, + 0x2A, 0x96, 0xE4, 0xAE, 0x34, 0x62, 0xC9, 0x60, 0x03, 0xCD, 0xDA, 0x87, 0xDB, 0x56, 0x1A, 0xF2, 0xCE, 0x3C, 0x0B, 0xA1, 0xD9, 0x04, 0x13, 0xFD, 0xCE, 0x3C, 0xCF, 0x43, 0x90, 0xC0, 0x2C, 0x1C, + 0xB9, 0xF6, 0x54, 0xF4, 0x82, 0x0E, 0xC3, 0x30, 0x15, 0x45, 0x7D, 0x4A, 0x62, 0x9F, 0xBF, 0x39, 0x41, 0x9C, 0xAB, 0x76, 0x42, 0xD6, 0x88, 0x5E, 0x10, 0x3F, 0xCE, 0x0D, 0x42, 0x06, 0xCC, 0xE7, + 0xC1, 0x2C, 0x6F, 0xC4, 0x4F, 0xA3, 0x3A, 0xD0, 0x86, 0x4C, 0x33, 0x71, 0xA7, 0xCB, 0xE8, 0x20, 0xE3, 0xB3, 0x71, 0xB6, 0x56, 0xA3, 0x8F, 0x2E, 0x7F, 0xF1, 0x8F, 0xE4, 0xA5, 0x0C, 0x8A, 0xB3, + 0xF8, 0x5D, 0x78, 0x3F, 0xB5, 0x78, 0x35, 0xCE, 0xD8, 0x49, 0x0B, 0x84, 0xEE, 0x0D, 0x99, 0xAF, 0x0D, 0x64, 0xC4, 0x83, 0xCE, 0xB6, 0x36, 0x6F, 0xF5, 0x4F, 0x8A, 0xC8, 0xA4, 0x0D, 0xB1, 0xAF, + 0xA5, 0x73, 0xA4, 0xFB, 0x32, 0x6C, 0x74, 0xF0, 0x23, 0x6E, 0xCE, 0xF3, 0xDA, 0x71, 0x20, 0x66, 0x5C, 0xCE, 0x05, 0xDD, 0x65, 0x4B, 0x50, 0x71, 0x72, 0x3A, 0x83, 0x48, 0xE7, 0xCD, 0x77, 0x93, + 0x51, 0x38, 0x19, 0xB6, 0x1C, 0xB6, 0x4E, 0x13, 0x28, 0xE8, 0xB2, 0x2E, 0x76, 0x64, 0xBD, 0x6B, 0x41, 0xB5, 0x71, 0x0D, 0x19, 0xEA, 0x88, 0x09, 0xD4, 0x45, 0x08, 0x50, 0xE9, 0x07, 0xDF, 0xC4, + 0xD0, 0xB7, 0x5F, 0x58, 0x8C, 0xEC, 0xE9, 0x62, 0xE9, 0xE0, 0x93, 0x7C, 0xE1, 0x40, 0x24, 0x46, 0xA4, 0xD2, 0x89, 0x1A, 0x46, 0xE6, 0x61, 0x7F, 0xB2, 0x9D, 0x4F, 0xCD, 0x71, 0x26, 0x06, 0xF7, + 0x81, 0x9E, 0xCA, 0x60, 0xF7, 0xE0, 0xD5, 0xB1, 0x9E, 0x7F, 0xFB, 0x57, 0xC7, 0x3C, 0x16, 0xFF, 0xEE, 0xB9, 0x00, 0x38, 0x41, 0x0C, 0xB9, 0xFC, 0xBB, 0x5E, 0x9D, 0x51, 0xEB, 0x3E, 0xB6, 0x29, + 0x7E, 0x9F, 0xF6, 0xAB, 0x70, 0x88, 0xFE, 0x2D, 0x9B, 0x23, 0x7B, 0xC2, 0x4C, 0xF7, 0xF8, 0x29, 0x01, 0x18, 0xA5, 0xE0, 0xE0, 0x0A, 0x0B, 0x90, 0x3F, 0xB6, 0x37, 0x5C, 0x84, 0x81, 0x76, 0xCD, + 0x0A, 0x8C, 0x88, 0x75, 0xCC, 0x59, 0x19, 0x9C, 0xDA, 0x11, 0xA8, 0x7A, 0x78, 0xF6, 0x5C, 0xC4, 0x04, 0x33, 0x0B, 0x08, 0x75, 0x71, 0xFD, 0x06, 0x33, 0xE2, 0x71, 0x29, 0xFD, 0xAB, 0x5A, 0x8A, + 0x1F, 0x79, 0x3E, 0x52, 0x41, 0x2B, 0x00, 0x83, 0xFD, 0x5C, 0x74, 0xDB, 0x3C, 0xF6, 0x0C, 0x25, 0x43, 0xCE, 0x7C, 0x91, 0xB2, 0x80, 0x0E, 0x40, 0x20, 0x3F, 0x8D, 0x99, 0xFE, 0x5F, 0xDE, 0x5B, + 0x10, 0x8E, 0x7E, 0xDC, 0x80, 0xEB, 0xB9, 0xBB, 0x34, 0x98, 0x6E, 0xC5, 0xC5, 0xA8, 0xF5, 0x80, 0xE7, 0x57, 0x52, 0x90, 0x7F, 0xF0, 0xF2, 0x94, 0xC8, 0x66, 0xC2, 0xCF, 0x1F, 0x36, 0x2E, 0x84, + 0x0B, 0x68, 0x81, 0xBD, 0x43, 0x21, 0x92, 0x01, 0x78, 0x1C, 0x63, 0xB0, 0x03, 0x9A, 0x95, 0xBC, 0xFB, 0x4A, 0x0F, 0xEC, 0xE5, 0x69, 0xDF, 0x00, 0x52, 0x3C, 0xE9, 0xC0, 0x84, 0xB0, 0x22, 0xB3, + 0xB0, 0x22, 0x24, 0x2E, 0x28, 0x41, 0x97, 0x96, 0xAC, 0xF0, 0xA0, 0xC9, 0x95, 0xF9, 0x48, 0xDB, 0xFF, 0xFD, 0x30, 0xD7, 0x7E, 0xD1, 0x05, 0xA3, 0xC9, 0x94, 0x3C, 0x40, 0x6B, 0x30, 0x5B, 0xC8, + 0x1A, 0x6A, 0x24, 0x8A, 0x29, 0x15, 0x48, 0xF2, 0xA6, 0x7F, 0x43, 0x8D, 0x96, 0x6A, 0x57, 0xD5, 0x3F, 0x4B, 0x7B, 0xE1, 0x53, 0x54, 0xE5, 0x81, 0xBE, 0x16, 0xF7, 0xAD, 0x64, 0xD1, 0x64, 0xE8, + 0x57, 0x87, 0xDF, 0x58, 0x49, 0xC8, 0x10, 0xAF, 0xC2, 0x8D, 0x06, 0x48, 0x2F, 0x44, 0x1B, 0x5F, 0xDE, 0x3D, 0xB2, 0xED, 0x36, 0xDD, 0x25, 0xAA, 0x66, 0x64, 0xD4, 0xD4, 0x3F, 0xFA, 0x32, 0xED, + 0xA2, 0x56, 0x89, 0xC9, 0xF4, 0xA5, 0xD5, 0x14, 0xFC, 0x66, 0x23, 0x1C, 0x54, 0x01, 0x52, 0x09, 0x22, 0x52, 0x44, 0x38, 0xEF, 0x1D, 0xC7, 0x8D, 0x69, 0x3C, 0x97, 0x18, 0xDE, 0xBB, 0xD2, 0x43, + 0x31, 0x26, 0x74, 0xC8, 0x99, 0xF1, 0x89, 0x10, 0xE3, 0x89, 0xC8, 0xEB, 0xE5, 0x05, 0x82, 0x4B, 0xCC, 0x42, 0xCD, 0x4A, 0x9A, 0xCE, 0x19, 0x37, 0x68, 0x22, 0x02, 0x19, 0x01, 0x1F, 0x3B, 0x1F, + 0x33, 0x54, 0x27, 0xBF, 0xF9, 0xE8, 0xBD, 0xED, 0x5C, 0x08, 0x71, 0x1A, 0x09, 0xC2, 0xB7, 0x1C, 0xB9, 0x64, 0xC5, 0x6A, 0x83, 0x93, 0xBF, 0xD2, 0xB5, 0x6E, 0x9B, 0x6B, 0x2F, 0x51, 0x3E, 0x68, + 0x25, 0x87, 0xDC, 0x1B, 0x8E, 0xD1, 0x96, 0x06, 0x63, 0x26, 0x87, 0x10, 0x25, 0x62, 0x80, 0x36, 0x70, 0x00, 0x63, 0x17, 0x6D, 0x34, 0x5D, 0xE3, 0x84, 0xE1, 0x82, 0xD6, 0xC4, 0x17, 0xA3, 0x2A, + 0xB1, 0x10, 0x95, 0xEF, 0x59, 0xBB, 0x4D, 0x17, 0x1B, 0x9C, 0xF8, 0x1D, 0x17, 0xAC, 0x42, 0x66, 0x4D, 0xED, 0x93, 0x3C, 0xCB, 0x72, 0x2C, 0x69, 0x85, 0x7F, 0xFC, 0x53, 0xC8, 0xE7, 0xF2, 0x47, + 0x4B, 0x0C, 0xB2, 0xDF, 0xF2, 0xDD, 0xC8, 0xA5, 0xC6, 0x01, 0xC8, 0x4A, 0x70, 0x19, 0x81, 0x19, 0x9B, 0xCC, 0xF7, 0x41, 0x12, 0xA6, 0xEC, 0x06, 0x2C, 0x4F, 0xEB, 0x60, 0x1A, 0x02, 0x8A, 0xF0, + 0x10, 0x32, 0xAD, 0xB6, 0xBD, 0x15, 0xD4, 0xC2, 0xB9, 0x55, 0x0A, 0xA8, 0x50, 0xAD, 0x62, 0xCC, 0xC3, 0xA3, 0x66, 0x5D, 0x52, 0x12, 0xB1, 0x2E, 0x0F, 0xD5, 0xC5, 0x32, 0x6A, 0x1E, 0x5E, 0xB1, + 0xF1, 0x0D, 0x55, 0x7D, 0x94, 0x60, 0x5E, 0x8E, 0x3F, 0x35, 0x6E, 0x08, 0xFF, 0x7F, 0xD8, 0x84, 0xED, 0x3C, 0x42, 0x05, 0x46, 0x35, 0x94, 0xC9, 0xAF, 0x2F, 0x39, 0xE4, 0xB1, 0x27, 0x46, 0x95, + 0x23, 0x4B, 0x54, 0xEE, 0xCE, 0xD9, 0x3F, 0x46, 0x0E, 0xDF, 0x1A, 0x13, 0xC2, 0xCB, 0x4B, 0x17, 0xD3, 0x22, 0xF6, 0xF7, 0x9F, 0xE1, 0x6F, 0x03, 0x57, 0xC1, 0xC4, 0x73, 0x98, 0x63, 0xE7, 0x96, + 0x79, 0x1F, 0x86, 0x47, 0xFA, 0xBF, 0x73, 0x0A, 0xB0, 0x0E, 0x0D, 0xA5, 0x09, 0x70, 0x6D, 0x94, 0x57, 0x17, 0x40, 0xF6, 0x1F, 0x7B, 0xAF, 0x36, 0x6D, 0x27, 0x74, 0xC9, 0xB5, 0xB8, 0xC6, 0x1D, + 0xD6, 0xBE, 0x98, 0x19, 0xA6, 0x02, 0x8B, 0x26, 0x4B, 0xB2, 0xE4, 0xAE, 0xA5, 0x4B, 0x56, 0xD4, 0xEC, 0xAB, 0x5B, 0x52, 0x8C, 0xE0, 0xC0, 0xC0, 0xCC, 0xDB, 0x73, 0x02, 0x33, 0x52, 0xCB, 0x00, + 0x44, 0x5B, 0xAB, 0x6F, 0x74, 0x67, 0xB4, 0x64, 0x4D, 0x43, 0x61, 0xC4, 0x64, 0xFA, 0xC6, 0xB5, 0xB1, 0x37, 0xD3, 0x23, 0x91, 0x02, 0x1B, 0x47, 0x5F, 0xCB, 0x5F, 0x31, 0x77, 0x4F, 0xD8, 0xEC, + 0xAB, 0xDF, 0x65, 0x47, 0x5F, 0x25, 0x57, 0x4C, 0x65, 0x55, 0x9C, 0xB3, 0x31, 0xF4, 0x1C, 0x0F, 0x49, 0x8B, 0x74, 0xDD, 0x94, 0x1C, 0x34, 0x4C, 0x50, 0xD8, 0xE6, 0x4F, 0x95, 0x78, 0x71, 0x4A, + 0x32, 0x56, 0x1F, 0xAA, 0xCE, 0xAF, 0x78, 0x14, 0x8E, 0x6D, 0xA4, 0xB5, 0x66, 0x82, 0x69, 0x25, 0x71, 0x4B, 0x17, 0x10, 0x8A, 0xFD, 0xD5, 0x46, 0x38, 0x5A, 0x3C, 0xD4, 0x54, 0xD5, 0xCA, 0xA1, + 0x69, 0x60, 0x91, 0x62, 0x82, 0xA4, 0x7C, 0x43, 0x15, 0xCE, 0x23, 0x6B, 0xD9, 0xE3, 0x25, 0x5C, 0x60, 0x4E, 0xBD, 0xC3, 0x97, 0x72, 0xDB, 0x5C, 0xE0, 0xB2, 0x36, 0xA0, 0x82, 0x05, 0x05, 0x03, + 0x82, 0x05, 0x01, 0x00, 0x61, 0x77, 0xE3, 0xDE, 0x0D, 0x4F, 0x1E, 0xF5, 0x84, 0x77, 0x35, 0x94, 0x7B, 0x56, 0xD0, 0x8E, 0x84, 0x1D, 0xB2, 0x44, 0x4F, 0xA2, 0xB7, 0x29, 0xAD, 0xEB, 0x14, 0x17, + 0xCA, 0x7A, 0xDF, 0x42, 0xA1, 0x49, 0x0C, 0x5A, 0x09, 0x7F, 0x00, 0x27, 0x60, 0xC1, 0xFC, 0x41, 0x9B, 0xE8, 0x32, 0x5A, 0xAD, 0x01, 0x97, 0xC5, 0x2C, 0xED, 0x80, 0xD3, 0xDF, 0x18, 0xE7, 0x77, + 0x42, 0x65, 0xB2, 0x89, 0x91, 0x2C, 0xEC, 0xA1, 0xBE, 0x3A, 0x90, 0xD8, 0xA4, 0xFD, 0xE6, 0x5C, 0x84, 0xC6, 0x10, 0x86, 0x4E, 0x47, 0xDE, 0xEC, 0xAE, 0x3E, 0xEA, 0x44, 0x30, 0xB9, 0x90, 0x95, + 0x59, 0x40, 0x8D, 0x11, 0xA6, 0xAB, 0xDB, 0x7D, 0xB9, 0x33, 0x6D, 0xF7, 0xF9, 0x6E, 0xAB, 0x48, 0x64, 0xA6, 0x57, 0x97, 0x91, 0x26, 0x5F, 0xA5, 0x6C, 0x34, 0x8C, 0xB7, 0xD2, 0xDD, 0xC9, 0x0E, + 0x13, 0x3A, 0x95, 0xC3, 0xF6, 0xB1, 0x36, 0x01, 0x42, 0x9F, 0x54, 0x08, 0xBD, 0x99, 0x9A, 0xA4, 0x79, 0xC1, 0x01, 0x81, 0x59, 0x55, 0x0E, 0xC5, 0x5A, 0x11, 0x3C, 0x49, 0x3B, 0xE6, 0x48, 0xF4, + 0xE0, 0x36, 0xDD, 0x4F, 0x8C, 0x80, 0x9E, 0x03, 0x6B, 0x4F, 0xBB, 0x91, 0x8C, 0x2C, 0x48, 0x4A, 0xD8, 0xE1, 0x74, 0x7A, 0xE0, 0x55, 0x85, 0xAB, 0x43, 0x3F, 0xDF, 0x46, 0x1A, 0xF0, 0x3C, 0x25, + 0xA7, 0x73, 0x70, 0x07, 0x21, 0xAA, 0x05, 0xF7, 0x37, 0x9F, 0xE7, 0xF5, 0xED, 0x96, 0x17, 0x5D, 0x40, 0x21, 0x07, 0x6E, 0x7F, 0x52, 0xB6, 0x03, 0x08, 0xEF, 0xF5, 0xD4, 0x2B, 0xA6, 0xE0, 0x93, + 0xB3, 0xD0, 0x81, 0x5E, 0xB3, 0x49, 0x66, 0x46, 0xE4, 0x92, 0x30, 0xA9, 0xB3, 0x5C, 0x8D, 0x41, 0x90, 0x0C, 0x2B, 0xB8, 0xD3, 0xB4, 0x46, 0xA2, 0x31, 0x27, 0xF7, 0xE0, 0x96, 0xD8, 0x5A, 0x1C, + 0x79, 0x4A, 0xD4, 0xC8, 0x92, 0x77, 0x90, 0x4F, 0xC6, 0xBF, 0xEC, 0x57, 0xB1, 0xCD, 0xD8, 0x0D, 0xF9, 0x95, 0x50, 0x30, 0xFD, 0xCA, 0x74, 0x1A, 0xFB, 0xDA, 0xC8, 0x27, 0xB1, 0x3C, 0xCD, 0x54, + 0x03, 0x58, 0x8A, 0xF4, 0x64, 0x40, 0x03, 0xC2, 0x26, 0x5D, 0xFA, 0x4D, 0x41, 0x9D, 0xBC, 0xCD, 0x20, 0x64, 0x89, 0x23, 0x86, 0x51, 0x8B, 0xE9, 0xD5, 0x1C, 0x16, 0x49, 0x82, 0x75, 0xEB, 0xEC, + 0xF5, 0xCD, 0xC7, 0xA8, 0x20, 0xF2, 0xC2, 0x93, 0x14, 0xAC, 0x4A, 0x6F, 0x08, 0xB2, 0x25, 0x2A, 0xD3, 0xCF, 0xB1, 0x99, 0xAA, 0x42, 0xFE, 0x0B, 0x4F, 0xB5, 0x71, 0x97, 0x5C, 0x10, 0x20, 0xD9, + 0x49, 0xE1, 0x94, 0xEE, 0x1E, 0xAD, 0x93, 0x7B, 0xFB, 0x55, 0x0B, 0xB3, 0xBA, 0x8E, 0x35, 0x7A, 0x02, 0x9C, 0x29, 0xF0, 0x77, 0x55, 0x46, 0x02, 0xE1, 0xCA, 0x2F, 0x22, 0x89, 0xCB, 0x91, 0x69, + 0x94, 0x1C, 0x3A, 0xAF, 0xDB, 0x8E, 0x58, 0xC7, 0xF2, 0xAC, 0x77, 0x29, 0x1F, 0xB4, 0x14, 0x7C, 0x65, 0xF6, 0xB0, 0x31, 0xD3, 0xEB, 0xA4, 0x2F, 0x2A, 0xCF, 0xD9, 0x44, 0x8A, 0x5B, 0xC2, 0x2B, + 0x47, 0x6E, 0x07, 0xCC, 0xCE, 0xDA, 0x23, 0x06, 0xC5, 0x54, 0xEC, 0x9B, 0x7A, 0xB6, 0x55, 0xF1, 0xD7, 0x31, 0x8C, 0x2B, 0x7E, 0x67, 0xD5, 0xF6, 0x9B, 0xED, 0xF5, 0x60, 0x00, 0xFD, 0xA9, 0x89, + 0x86, 0xB5, 0xAB, 0x1B, 0x3A, 0x22, 0xD8, 0xDF, 0xD6, 0x68, 0x16, 0x97, 0xB2, 0x3A, 0x55, 0xC9, 0x6E, 0x87, 0x10, 0xF3, 0xF9, 0x8C, 0x04, 0x4F, 0xB1, 0x5F, 0x60, 0x63, 0x13, 0xEE, 0x56, 0xC0, + 0xF1, 0xF5, 0xCA, 0x0F, 0x51, 0x2E, 0x08, 0x48, 0x4F, 0xCB, 0x35, 0x8E, 0x6E, 0x52, 0x8F, 0xFA, 0x89, 0xF8, 0xA8, 0x66, 0xCC, 0xFF, 0x3C, 0x0C, 0x58, 0x13, 0x14, 0x7E, 0xC5, 0x9A, 0xF0, 0x47, + 0x0C, 0x4A, 0xAD, 0x01, 0x41, 0xD3, 0x4F, 0x10, 0x1D, 0xA2, 0xE5, 0xE1, 0xBD, 0x52, 0xD0, 0xD4, 0xC9, 0xB1, 0x3B, 0x3E, 0x3D, 0x87, 0xD1, 0x58, 0x61, 0x05, 0x79, 0x67, 0x54, 0xE7, 0x97, 0x8C, + 0xA1, 0xC6, 0x8A, 0x7D, 0x85, 0xDF, 0x11, 0x2B, 0x7A, 0xB9, 0x21, 0xB3, 0x59, 0xA9, 0xF0, 0x3C, 0xBD, 0x27, 0xA7, 0xEA, 0xC8, 0x7A, 0x9A, 0x80, 0xB0, 0xB2, 0x6B, 0x4C, 0x96, 0x57, 0xED, 0x85, + 0xAD, 0x7F, 0xA2, 0x61, 0x6A, 0xB3, 0x45, 0xEB, 0x82, 0x26, 0xF6, 0x9F, 0xC0, 0xF4, 0x81, 0x83, 0xFF, 0x57, 0x4B, 0xCD, 0x76, 0x7B, 0x56, 0x76, 0x41, 0x3A, 0xDB, 0x12, 0xEA, 0x21, 0x50, 0xA0, + 0xE9, 0x76, 0x83, 0xEE, 0x54, 0x24, 0x3C, 0x25, 0xB7, 0xEA, 0x8A, 0x71, 0x86, 0x06, 0xF8, 0x69, 0x93, 0xD8, 0xD0, 0xDA, 0xCE, 0x83, 0x4E, 0xD3, 0x41, 0xEE, 0xB7, 0x24, 0xFE, 0x3D, 0x5F, 0xF0, + 0xBC, 0x8B, 0x8A, 0x7B, 0x81, 0x04, 0xBA, 0x26, 0x9D, 0x34, 0x13, 0x3A, 0x4C, 0xF8, 0x30, 0x0A, 0x2D, 0x68, 0x84, 0x96, 0xB5, 0x9B, 0x6F, 0xCB, 0xC6, 0x1A, 0xE9, 0x60, 0x62, 0xEA, 0x1D, 0x8E, + 0x5B, 0x41, 0x0C, 0x56, 0x71, 0xF4, 0x24, 0x41, 0x7E, 0xD6, 0x93, 0x32, 0x9C, 0xD9, 0x83, 0x00, 0x1F, 0xFC, 0xD1, 0x00, 0x23, 0xD5, 0x98, 0x85, 0x9F, 0xB7, 0xAD, 0x5F, 0xD2, 0x63, 0x54, 0x71, + 0x17, 0x10, 0x06, 0x90, 0xC6, 0xCE, 0x74, 0x38, 0x95, 0x6E, 0x6C, 0xC5, 0x7F, 0x1B, 0x5D, 0xE5, 0x3B, 0xB0, 0xDC, 0x72, 0xCE, 0x9B, 0x6D, 0xEA, 0xA8, 0x57, 0x89, 0x59, 0x9A, 0x70, 0xF0, 0x05, + 0x1F, 0x1A, 0x0E, 0x25, 0xE8, 0x6D, 0x88, 0x8B, 0x00, 0xDF, 0x36, 0xBD, 0xBC, 0x93, 0xEF, 0x72, 0x17, 0xC4, 0x5A, 0xCE, 0x11, 0xC0, 0x79, 0x0D, 0x70, 0xE9, 0x95, 0x3E, 0x5B, 0x41, 0x7B, 0xA2, + 0xFD, 0x9A, 0x4C, 0xAF, 0x82, 0xF1, 0xFC, 0xE6, 0xF4, 0x5F, 0x53, 0xE2, 0x15, 0xB8, 0x35, 0x5E, 0xF6, 0x1D, 0x89, 0x1D, 0xF1, 0xC7, 0x94, 0x23, 0x1C, 0x16, 0x2D, 0xD2, 0x41, 0x64, 0xB5, 0x34, + 0xA9, 0xD4, 0x84, 0x67, 0xCD, 0xC3, 0x23, 0x62, 0x4C, 0x2F, 0x95, 0xD4, 0x40, 0x2F, 0xF9, 0xD6, 0x6A, 0xB1, 0x19, 0x1A, 0x81, 0x24, 0x14, 0x4A, 0xFA, 0x35, 0xD4, 0xE3, 0x1D, 0xC8, 0x6C, 0xAA, + 0x79, 0x7C, 0x31, 0xF6, 0x8B, 0x85, 0x85, 0x4C, 0xD9, 0x59, 0xC4, 0xFA, 0xC5, 0xEC, 0x53, 0xB3, 0xB5, 0x6D, 0x37, 0x4B, 0x88, 0x8A, 0x9E, 0x97, 0x9A, 0x65, 0x76, 0xB6, 0x34, 0x5E, 0xC8, 0x52, + 0x2C, 0x96, 0x06, 0x99, 0x02, 0x81, 0xBF, 0x3E, 0xF7, 0xC5, 0x94, 0x5D, 0x10, 0xFD, 0x21, 0xA2, 0xA1, 0xD2, 0xE5, 0x40, 0x4C, 0x5C, 0xF2, 0x12, 0x20, 0x64, 0x13, 0x91, 0xB9, 0x8B, 0xCF, 0x82, + 0x53, 0x98, 0x30, 0x5B, 0x56, 0xE5, 0x8B, 0x61, 0x1F, 0xE5, 0x25, 0x32, 0x03, 0xE3, 0xDF, 0x0D, 0x22, 0x46, 0x6A, 0x73, 0xB3, 0xF0, 0xFB, 0xE4, 0x3B, 0x9A, 0x62, 0x92, 0x80, 0x91, 0x89, 0x8B, + 0x8A, 0x0E, 0x5B, 0x26, 0x9D, 0xB5, 0x86, 0xB0, 0xE4, 0xDD, 0xEF, 0x50, 0xD6, 0x82, 0xA1, 0x2D, 0x2C, 0x1B, 0xE8, 0x24, 0x14, 0x9A, 0xA2, 0x54, 0xC6, 0x38, 0x1B, 0xB4, 0x12, 0xD7, 0x7C, 0x3F, + 0x9A, 0xA9, 0x02, 0xB6, 0x88, 0xC8, 0x17, 0x15, 0xA5, 0x9C, 0x83, 0x95, 0x58, 0x55, 0x6D, 0x35, 0xED, 0x4F, 0xC8, 0x3B, 0x4A, 0xB1, 0x81, 0x81, 0xF4, 0x0F, 0x73, 0xDC, 0xD7, 0x68, 0x60, 0xD8, + 0xD8, 0xBF, 0x94, 0x52, 0x02, 0x37, 0xC2, 0xAC, 0x0E, 0x46, 0x3B, 0xA0, 0x9E, 0x3C, 0x97, 0x82, 0x38, 0x0D, 0xC0, 0x7F, 0xE4, 0xFC, 0xBA, 0x34, 0x0C, 0xC2, 0x00, 0x34, 0x39, 0xFD, 0x23, 0x14, + 0x61, 0x06, 0x38, 0x07, 0x0D, 0x6C, 0x9E, 0xEA, 0x0A, 0x70, 0xBA, 0xE8, 0x3B, 0x5D, 0x5D, 0x3C, 0x5D, 0x3F, 0xDE, 0x26, 0xDD, 0x01, 0x60, 0x6C, 0x8C, 0x52, 0x01, 0x58, 0xE7, 0xE5, 0x10, 0x40, + 0x20, 0xF2, 0x48, 0xCE, 0xAA, 0x66, 0x64, 0x57, 0xC1, 0x0A, 0xEB, 0xF0, 0x68, 0xF8, 0xA3, 0xBD, 0x5C, 0xE7, 0xB5, 0x2C, 0x6A, 0xF0, 0xAB, 0xD5, 0x94, 0x4A, 0xF1, 0xAD, 0x47, 0x52, 0xC9, 0x11, + 0x39, 0x76, 0x08, 0x3C, 0x03, 0xB6, 0xC3, 0x4E, 0x1D, 0x47, 0xED, 0x69, 0x64, 0x4C, 0xAD, 0x78, 0x2C, 0x2F, 0x7D, 0x05, 0xF8, 0xA1, 0x48, 0x96, 0x1D, 0x96, 0x5F, 0xA2, 0xE1, 0x72, 0x3A, 0x8D, + 0xDE, 0xBC, 0x22, 0xA9, 0x0C, 0xD7, 0x83, 0xDD, 0x1F, 0x4D, 0xB3, 0x8F, 0xB9, 0xAE, 0x5A, 0x67, 0x14, 0xB3, 0xD9, 0x46, 0x78, 0x16, 0x43, 0xD3, 0x17, 0xB7, 0xDD, 0x79, 0x38, 0x1C, 0xF7, 0x89, + 0xA9, 0x58, 0x8B, 0xB3, 0xE1, 0x93, 0xB9, 0x2A, 0x0B, 0x60, 0xD6, 0xB0, 0x7D, 0x04, 0x7F, 0x69, 0x84, 0xB0, 0x60, 0x9E, 0xC5, 0x75, 0x43, 0xC3, 0x94, 0xCA, 0x8D, 0x5E, 0x5B, 0xCC, 0x2A, 0x73, + 0x1A, 0x79, 0x61, 0x8B, 0xD1, 0xE2, 0xE0, 0xDA, 0x87, 0x04, 0xAF, 0x98, 0xF2, 0x0F, 0x5F, 0x8F, 0x54, 0x52, 0xDD, 0xF6, 0x46, 0xB9, 0x5B, 0x34, 0x1D, 0xD7, 0xF0, 0xD2, 0xCC, 0x1F, 0xA1, 0x5B, + 0xD9, 0x89, 0x5C, 0xD5, 0xB6, 0x5A, 0xA1, 0xCB, 0x94, 0xB5, 0xE2, 0xE7, 0x88, 0xFD, 0xA9, 0x82, 0x5B, 0x65, 0x66, 0x39, 0x19, 0x3D, 0x98, 0x32, 0x81, 0x54, 0xA4, 0xF2, 0xC3, 0x54, 0x95, 0xA3, + 0x8B, 0x6E, 0xA0, 0xD2, 0xFF, 0xAA, 0xA3, 0x5D, 0xF9, 0x2C, 0x20, 0x3C, 0x7F, 0x31, 0xCB, 0xBC, 0xA7, 0xBD, 0x03, 0xC3, 0xC2, 0x30, 0x21, 0x90, 0xCE, 0xCD, 0x16, 0x1F, 0xD4, 0x92, 0x37, 0xE4, + 0xF8, 0x39, 0xE3, 0xF3, + }, + .spki_len = 1350, + .spki = { + 0x30, 0x82, 0x05, 0x42, 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0B, 0x07, 0x04, 0x04, 0x05, 0x00, 0x03, 0x82, 0x05, 0x2D, 0x00, 0x30, 0x82, 0x05, 0x28, 0x03, 0x21, + 0x00, 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, 0x38, 0xD5, 0x06, 0xD8, 0x5B, + 0xEF, 0x03, 0x82, 0x05, 0x01, 0x00, 0x61, 0x77, 0xE3, 0xDE, 0x0D, 0x4F, 0x1E, 0xF5, 0x84, 0x77, 0x35, 0x94, 0x7B, 0x56, 0xD0, 0x8E, 0x84, 0x1D, 0xB2, 0x44, 0x4F, 0xA2, 0xB7, 0x29, 0xAD, 0xEB, + 0x14, 0x17, 0xCA, 0x7A, 0xDF, 0x42, 0xA1, 0x49, 0x0C, 0x5A, 0x09, 0x7F, 0x00, 0x27, 0x60, 0xC1, 0xFC, 0x41, 0x9B, 0xE8, 0x32, 0x5A, 0xAD, 0x01, 0x97, 0xC5, 0x2C, 0xED, 0x80, 0xD3, 0xDF, 0x18, + 0xE7, 0x77, 0x42, 0x65, 0xB2, 0x89, 0x91, 0x2C, 0xEC, 0xA1, 0xBE, 0x3A, 0x90, 0xD8, 0xA4, 0xFD, 0xE6, 0x5C, 0x84, 0xC6, 0x10, 0x86, 0x4E, 0x47, 0xDE, 0xEC, 0xAE, 0x3E, 0xEA, 0x44, 0x30, 0xB9, + 0x90, 0x95, 0x59, 0x40, 0x8D, 0x11, 0xA6, 0xAB, 0xDB, 0x7D, 0xB9, 0x33, 0x6D, 0xF7, 0xF9, 0x6E, 0xAB, 0x48, 0x64, 0xA6, 0x57, 0x97, 0x91, 0x26, 0x5F, 0xA5, 0x6C, 0x34, 0x8C, 0xB7, 0xD2, 0xDD, + 0xC9, 0x0E, 0x13, 0x3A, 0x95, 0xC3, 0xF6, 0xB1, 0x36, 0x01, 0x42, 0x9F, 0x54, 0x08, 0xBD, 0x99, 0x9A, 0xA4, 0x79, 0xC1, 0x01, 0x81, 0x59, 0x55, 0x0E, 0xC5, 0x5A, 0x11, 0x3C, 0x49, 0x3B, 0xE6, + 0x48, 0xF4, 0xE0, 0x36, 0xDD, 0x4F, 0x8C, 0x80, 0x9E, 0x03, 0x6B, 0x4F, 0xBB, 0x91, 0x8C, 0x2C, 0x48, 0x4A, 0xD8, 0xE1, 0x74, 0x7A, 0xE0, 0x55, 0x85, 0xAB, 0x43, 0x3F, 0xDF, 0x46, 0x1A, 0xF0, + 0x3C, 0x25, 0xA7, 0x73, 0x70, 0x07, 0x21, 0xAA, 0x05, 0xF7, 0x37, 0x9F, 0xE7, 0xF5, 0xED, 0x96, 0x17, 0x5D, 0x40, 0x21, 0x07, 0x6E, 0x7F, 0x52, 0xB6, 0x03, 0x08, 0xEF, 0xF5, 0xD4, 0x2B, 0xA6, + 0xE0, 0x93, 0xB3, 0xD0, 0x81, 0x5E, 0xB3, 0x49, 0x66, 0x46, 0xE4, 0x92, 0x30, 0xA9, 0xB3, 0x5C, 0x8D, 0x41, 0x90, 0x0C, 0x2B, 0xB8, 0xD3, 0xB4, 0x46, 0xA2, 0x31, 0x27, 0xF7, 0xE0, 0x96, 0xD8, + 0x5A, 0x1C, 0x79, 0x4A, 0xD4, 0xC8, 0x92, 0x77, 0x90, 0x4F, 0xC6, 0xBF, 0xEC, 0x57, 0xB1, 0xCD, 0xD8, 0x0D, 0xF9, 0x95, 0x50, 0x30, 0xFD, 0xCA, 0x74, 0x1A, 0xFB, 0xDA, 0xC8, 0x27, 0xB1, 0x3C, + 0xCD, 0x54, 0x03, 0x58, 0x8A, 0xF4, 0x64, 0x40, 0x03, 0xC2, 0x26, 0x5D, 0xFA, 0x4D, 0x41, 0x9D, 0xBC, 0xCD, 0x20, 0x64, 0x89, 0x23, 0x86, 0x51, 0x8B, 0xE9, 0xD5, 0x1C, 0x16, 0x49, 0x82, 0x75, + 0xEB, 0xEC, 0xF5, 0xCD, 0xC7, 0xA8, 0x20, 0xF2, 0xC2, 0x93, 0x14, 0xAC, 0x4A, 0x6F, 0x08, 0xB2, 0x25, 0x2A, 0xD3, 0xCF, 0xB1, 0x99, 0xAA, 0x42, 0xFE, 0x0B, 0x4F, 0xB5, 0x71, 0x97, 0x5C, 0x10, + 0x20, 0xD9, 0x49, 0xE1, 0x94, 0xEE, 0x1E, 0xAD, 0x93, 0x7B, 0xFB, 0x55, 0x0B, 0xB3, 0xBA, 0x8E, 0x35, 0x7A, 0x02, 0x9C, 0x29, 0xF0, 0x77, 0x55, 0x46, 0x02, 0xE1, 0xCA, 0x2F, 0x22, 0x89, 0xCB, + 0x91, 0x69, 0x94, 0x1C, 0x3A, 0xAF, 0xDB, 0x8E, 0x58, 0xC7, 0xF2, 0xAC, 0x77, 0x29, 0x1F, 0xB4, 0x14, 0x7C, 0x65, 0xF6, 0xB0, 0x31, 0xD3, 0xEB, 0xA4, 0x2F, 0x2A, 0xCF, 0xD9, 0x44, 0x8A, 0x5B, + 0xC2, 0x2B, 0x47, 0x6E, 0x07, 0xCC, 0xCE, 0xDA, 0x23, 0x06, 0xC5, 0x54, 0xEC, 0x9B, 0x7A, 0xB6, 0x55, 0xF1, 0xD7, 0x31, 0x8C, 0x2B, 0x7E, 0x67, 0xD5, 0xF6, 0x9B, 0xED, 0xF5, 0x60, 0x00, 0xFD, + 0xA9, 0x89, 0x86, 0xB5, 0xAB, 0x1B, 0x3A, 0x22, 0xD8, 0xDF, 0xD6, 0x68, 0x16, 0x97, 0xB2, 0x3A, 0x55, 0xC9, 0x6E, 0x87, 0x10, 0xF3, 0xF9, 0x8C, 0x04, 0x4F, 0xB1, 0x5F, 0x60, 0x63, 0x13, 0xEE, + 0x56, 0xC0, 0xF1, 0xF5, 0xCA, 0x0F, 0x51, 0x2E, 0x08, 0x48, 0x4F, 0xCB, 0x35, 0x8E, 0x6E, 0x52, 0x8F, 0xFA, 0x89, 0xF8, 0xA8, 0x66, 0xCC, 0xFF, 0x3C, 0x0C, 0x58, 0x13, 0x14, 0x7E, 0xC5, 0x9A, + 0xF0, 0x47, 0x0C, 0x4A, 0xAD, 0x01, 0x41, 0xD3, 0x4F, 0x10, 0x1D, 0xA2, 0xE5, 0xE1, 0xBD, 0x52, 0xD0, 0xD4, 0xC9, 0xB1, 0x3B, 0x3E, 0x3D, 0x87, 0xD1, 0x58, 0x61, 0x05, 0x79, 0x67, 0x54, 0xE7, + 0x97, 0x8C, 0xA1, 0xC6, 0x8A, 0x7D, 0x85, 0xDF, 0x11, 0x2B, 0x7A, 0xB9, 0x21, 0xB3, 0x59, 0xA9, 0xF0, 0x3C, 0xBD, 0x27, 0xA7, 0xEA, 0xC8, 0x7A, 0x9A, 0x80, 0xB0, 0xB2, 0x6B, 0x4C, 0x96, 0x57, + 0xED, 0x85, 0xAD, 0x7F, 0xA2, 0x61, 0x6A, 0xB3, 0x45, 0xEB, 0x82, 0x26, 0xF6, 0x9F, 0xC0, 0xF4, 0x81, 0x83, 0xFF, 0x57, 0x4B, 0xCD, 0x76, 0x7B, 0x56, 0x76, 0x41, 0x3A, 0xDB, 0x12, 0xEA, 0x21, + 0x50, 0xA0, 0xE9, 0x76, 0x83, 0xEE, 0x54, 0x24, 0x3C, 0x25, 0xB7, 0xEA, 0x8A, 0x71, 0x86, 0x06, 0xF8, 0x69, 0x93, 0xD8, 0xD0, 0xDA, 0xCE, 0x83, 0x4E, 0xD3, 0x41, 0xEE, 0xB7, 0x24, 0xFE, 0x3D, + 0x5F, 0xF0, 0xBC, 0x8B, 0x8A, 0x7B, 0x81, 0x04, 0xBA, 0x26, 0x9D, 0x34, 0x13, 0x3A, 0x4C, 0xF8, 0x30, 0x0A, 0x2D, 0x68, 0x84, 0x96, 0xB5, 0x9B, 0x6F, 0xCB, 0xC6, 0x1A, 0xE9, 0x60, 0x62, 0xEA, + 0x1D, 0x8E, 0x5B, 0x41, 0x0C, 0x56, 0x71, 0xF4, 0x24, 0x41, 0x7E, 0xD6, 0x93, 0x32, 0x9C, 0xD9, 0x83, 0x00, 0x1F, 0xFC, 0xD1, 0x00, 0x23, 0xD5, 0x98, 0x85, 0x9F, 0xB7, 0xAD, 0x5F, 0xD2, 0x63, + 0x54, 0x71, 0x17, 0x10, 0x06, 0x90, 0xC6, 0xCE, 0x74, 0x38, 0x95, 0x6E, 0x6C, 0xC5, 0x7F, 0x1B, 0x5D, 0xE5, 0x3B, 0xB0, 0xDC, 0x72, 0xCE, 0x9B, 0x6D, 0xEA, 0xA8, 0x57, 0x89, 0x59, 0x9A, 0x70, + 0xF0, 0x05, 0x1F, 0x1A, 0x0E, 0x25, 0xE8, 0x6D, 0x88, 0x8B, 0x00, 0xDF, 0x36, 0xBD, 0xBC, 0x93, 0xEF, 0x72, 0x17, 0xC4, 0x5A, 0xCE, 0x11, 0xC0, 0x79, 0x0D, 0x70, 0xE9, 0x95, 0x3E, 0x5B, 0x41, + 0x7B, 0xA2, 0xFD, 0x9A, 0x4C, 0xAF, 0x82, 0xF1, 0xFC, 0xE6, 0xF4, 0x5F, 0x53, 0xE2, 0x15, 0xB8, 0x35, 0x5E, 0xF6, 0x1D, 0x89, 0x1D, 0xF1, 0xC7, 0x94, 0x23, 0x1C, 0x16, 0x2D, 0xD2, 0x41, 0x64, + 0xB5, 0x34, 0xA9, 0xD4, 0x84, 0x67, 0xCD, 0xC3, 0x23, 0x62, 0x4C, 0x2F, 0x95, 0xD4, 0x40, 0x2F, 0xF9, 0xD6, 0x6A, 0xB1, 0x19, 0x1A, 0x81, 0x24, 0x14, 0x4A, 0xFA, 0x35, 0xD4, 0xE3, 0x1D, 0xC8, + 0x6C, 0xAA, 0x79, 0x7C, 0x31, 0xF6, 0x8B, 0x85, 0x85, 0x4C, 0xD9, 0x59, 0xC4, 0xFA, 0xC5, 0xEC, 0x53, 0xB3, 0xB5, 0x6D, 0x37, 0x4B, 0x88, 0x8A, 0x9E, 0x97, 0x9A, 0x65, 0x76, 0xB6, 0x34, 0x5E, + 0xC8, 0x52, 0x2C, 0x96, 0x06, 0x99, 0x02, 0x81, 0xBF, 0x3E, 0xF7, 0xC5, 0x94, 0x5D, 0x10, 0xFD, 0x21, 0xA2, 0xA1, 0xD2, 0xE5, 0x40, 0x4C, 0x5C, 0xF2, 0x12, 0x20, 0x64, 0x13, 0x91, 0xB9, 0x8B, + 0xCF, 0x82, 0x53, 0x98, 0x30, 0x5B, 0x56, 0xE5, 0x8B, 0x61, 0x1F, 0xE5, 0x25, 0x32, 0x03, 0xE3, 0xDF, 0x0D, 0x22, 0x46, 0x6A, 0x73, 0xB3, 0xF0, 0xFB, 0xE4, 0x3B, 0x9A, 0x62, 0x92, 0x80, 0x91, + 0x89, 0x8B, 0x8A, 0x0E, 0x5B, 0x26, 0x9D, 0xB5, 0x86, 0xB0, 0xE4, 0xDD, 0xEF, 0x50, 0xD6, 0x82, 0xA1, 0x2D, 0x2C, 0x1B, 0xE8, 0x24, 0x14, 0x9A, 0xA2, 0x54, 0xC6, 0x38, 0x1B, 0xB4, 0x12, 0xD7, + 0x7C, 0x3F, 0x9A, 0xA9, 0x02, 0xB6, 0x88, 0xC8, 0x17, 0x15, 0xA5, 0x9C, 0x83, 0x95, 0x58, 0x55, 0x6D, 0x35, 0xED, 0x4F, 0xC8, 0x3B, 0x4A, 0xB1, 0x81, 0x81, 0xF4, 0x0F, 0x73, 0xDC, 0xD7, 0x68, + 0x60, 0xD8, 0xD8, 0xBF, 0x94, 0x52, 0x02, 0x37, 0xC2, 0xAC, 0x0E, 0x46, 0x3B, 0xA0, 0x9E, 0x3C, 0x97, 0x82, 0x38, 0x0D, 0xC0, 0x7F, 0xE4, 0xFC, 0xBA, 0x34, 0x0C, 0xC2, 0x00, 0x34, 0x39, 0xFD, + 0x23, 0x14, 0x61, 0x06, 0x38, 0x07, 0x0D, 0x6C, 0x9E, 0xEA, 0x0A, 0x70, 0xBA, 0xE8, 0x3B, 0x5D, 0x5D, 0x3C, 0x5D, 0x3F, 0xDE, 0x26, 0xDD, 0x01, 0x60, 0x6C, 0x8C, 0x52, 0x01, 0x58, 0xE7, 0xE5, + 0x10, 0x40, 0x20, 0xF2, 0x48, 0xCE, 0xAA, 0x66, 0x64, 0x57, 0xC1, 0x0A, 0xEB, 0xF0, 0x68, 0xF8, 0xA3, 0xBD, 0x5C, 0xE7, 0xB5, 0x2C, 0x6A, 0xF0, 0xAB, 0xD5, 0x94, 0x4A, 0xF1, 0xAD, 0x47, 0x52, + 0xC9, 0x11, 0x39, 0x76, 0x08, 0x3C, 0x03, 0xB6, 0xC3, 0x4E, 0x1D, 0x47, 0xED, 0x69, 0x64, 0x4C, 0xAD, 0x78, 0x2C, 0x2F, 0x7D, 0x05, 0xF8, 0xA1, 0x48, 0x96, 0x1D, 0x96, 0x5F, 0xA2, 0xE1, 0x72, + 0x3A, 0x8D, 0xDE, 0xBC, 0x22, 0xA9, 0x0C, 0xD7, 0x83, 0xDD, 0x1F, 0x4D, 0xB3, 0x8F, 0xB9, 0xAE, 0x5A, 0x67, 0x14, 0xB3, 0xD9, 0x46, 0x78, 0x16, 0x43, 0xD3, 0x17, 0xB7, 0xDD, 0x79, 0x38, 0x1C, + 0xF7, 0x89, 0xA9, 0x58, 0x8B, 0xB3, 0xE1, 0x93, 0xB9, 0x2A, 0x0B, 0x60, 0xD6, 0xB0, 0x7D, 0x04, 0x7F, 0x69, 0x84, 0xB0, 0x60, 0x9E, 0xC5, 0x75, 0x43, 0xC3, 0x94, 0xCA, 0x8D, 0x5E, 0x5B, 0xCC, + 0x2A, 0x73, 0x1A, 0x79, 0x61, 0x8B, 0xD1, 0xE2, 0xE0, 0xDA, 0x87, 0x04, 0xAF, 0x98, 0xF2, 0x0F, 0x5F, 0x8F, 0x54, 0x52, 0xDD, 0xF6, 0x46, 0xB9, 0x5B, 0x34, 0x1D, 0xD7, 0xF0, 0xD2, 0xCC, 0x1F, + 0xA1, 0x5B, 0xD9, 0x89, 0x5C, 0xD5, 0xB6, 0x5A, 0xA1, 0xCB, 0x94, 0xB5, 0xE2, 0xE7, 0x88, 0xFD, 0xA9, 0x82, 0x5B, 0x65, 0x66, 0x39, 0x19, 0x3D, 0x98, 0x32, 0x81, 0x54, 0xA4, 0xF2, 0xC3, 0x54, + 0x95, 0xA3, 0x8B, 0x6E, 0xA0, 0xD2, 0xFF, 0xAA, 0xA3, 0x5D, 0xF9, 0x2C, 0x20, 0x3C, 0x7F, 0x31, 0xCB, 0xBC, 0xA7, 0xBD, 0x03, 0xC3, 0xC2, 0x30, 0x21, 0x90, 0xCE, 0xCD, 0x16, 0x1F, 0xD4, 0x92, + 0x37, 0xE4, 0xF8, 0x39, 0xE3, 0xF3, + }, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 2420, + .sig = { + 0xAF, 0x59, 0x20, 0x77, 0x46, 0x03, 0xD2, 0x0E, 0x98, 0xA7, 0x9A, 0xA3, 0xAB, 0xFA, 0x32, 0xB6, 0xE2, 0x25, 0x19, 0xE6, 0x73, 0xE3, 0x7A, 0xC4, 0xAC, 0x73, 0xFE, 0x85, 0x34, 0x1E, 0x2C, 0x29, + 0x23, 0xC1, 0x99, 0x2E, 0x1B, 0x0B, 0xBE, 0x38, 0x73, 0xD7, 0xC8, 0xFC, 0x56, 0x62, 0xF2, 0x07, 0xBF, 0x58, 0xEA, 0x38, 0x1C, 0xD4, 0xA3, 0xA0, 0xC0, 0x62, 0xDE, 0xC4, 0x5B, 0xDA, 0xF8, 0xBA, + 0x0A, 0xA5, 0x2B, 0xEF, 0x6F, 0xA1, 0x4F, 0x3F, 0x6C, 0xF2, 0x8F, 0x76, 0x20, 0xBF, 0x94, 0xA9, 0x2C, 0xC2, 0x7D, 0x04, 0x54, 0x14, 0xA6, 0x4D, 0x65, 0xC0, 0x14, 0x96, 0x30, 0x52, 0x80, 0x24, + 0x28, 0xBF, 0x39, 0x87, 0xA2, 0xD4, 0x75, 0x16, 0xCA, 0x5C, 0x78, 0xAA, 0xB9, 0x6B, 0x7B, 0xE1, 0x1B, 0xCA, 0x5F, 0x2C, 0x5A, 0x26, 0xF3, 0xFC, 0xE3, 0xA2, 0x6E, 0x8E, 0x09, 0xA2, 0x73, 0x8F, + 0x38, 0x6F, 0x75, 0xD4, 0x48, 0xF9, 0x37, 0xEF, 0x19, 0xA8, 0x46, 0xBD, 0x4D, 0xD9, 0x49, 0xCA, 0xAF, 0x36, 0xDB, 0x56, 0x29, 0x88, 0x4A, 0xF5, 0x3A, 0x02, 0x3E, 0x3F, 0x18, 0x0F, 0xE4, 0xC0, + 0xFA, 0xFF, 0x7B, 0xE5, 0xDF, 0xE4, 0xE8, 0x9A, 0xDE, 0x30, 0x95, 0xA6, 0x56, 0x00, 0x42, 0x14, 0x61, 0xAD, 0x08, 0xC1, 0x29, 0xD6, 0xCE, 0xA8, 0x51, 0xBB, 0x39, 0xC0, 0xD7, 0xA7, 0xD1, 0x51, + 0x40, 0x56, 0x89, 0xA0, 0x91, 0xFA, 0x4D, 0xEB, 0xAC, 0x37, 0x3C, 0xF5, 0x4A, 0xE0, 0x78, 0xF0, 0xAF, 0x75, 0x57, 0xBB, 0xC6, 0xF0, 0x6A, 0x53, 0x5A, 0xE8, 0x94, 0x9E, 0x0C, 0x65, 0x30, 0x8A, + 0x59, 0x84, 0x00, 0x72, 0x37, 0x52, 0x95, 0x80, 0x2D, 0x0E, 0x2C, 0xE9, 0xA3, 0xDA, 0x98, 0x42, 0x6A, 0x00, 0xFF, 0x03, 0xFE, 0x80, 0x21, 0x8C, 0x0E, 0xEC, 0x8E, 0xFE, 0x58, 0x1C, 0xB9, 0xCC, + 0x9A, 0x7D, 0x66, 0xB2, 0x06, 0x45, 0xA8, 0xCD, 0x04, 0x90, 0xD3, 0xCE, 0x4F, 0x7E, 0x6F, 0xEA, 0xE9, 0xC9, 0xEB, 0x7A, 0x57, 0xF9, 0x64, 0xD0, 0xEB, 0xC7, 0xC9, 0x0B, 0x7A, 0x9F, 0x86, 0x30, + 0x0B, 0x3E, 0x80, 0x95, 0xE6, 0x4D, 0x12, 0x94, 0xCF, 0xC4, 0xB4, 0xD9, 0xE2, 0x72, 0xE8, 0xFA, 0x8D, 0xB5, 0x70, 0x7D, 0x70, 0x04, 0xAF, 0x22, 0xDB, 0xFF, 0x9C, 0xFD, 0x48, 0x63, 0xDF, 0x57, + 0x3F, 0xE0, 0x04, 0x34, 0x1D, 0xA3, 0xCD, 0x4A, 0x30, 0x82, 0x53, 0x2C, 0x26, 0x20, 0x45, 0x5F, 0xA3, 0x7C, 0x56, 0x2B, 0xAF, 0xD5, 0x68, 0x4E, 0xA1, 0x28, 0xAF, 0xC7, 0x9E, 0x01, 0xFC, 0x9B, + 0x31, 0xE8, 0x43, 0x3B, 0xAD, 0x7C, 0x02, 0x9F, 0x2F, 0x13, 0xCC, 0x10, 0x59, 0x2D, 0x23, 0x32, 0xE3, 0xE0, 0x8B, 0x80, 0xD3, 0x50, 0x46, 0x3D, 0xE7, 0x27, 0x50, 0xB1, 0xF8, 0x06, 0xF4, 0x93, + 0xE1, 0x43, 0xBD, 0x5F, 0xCA, 0x7D, 0x16, 0x98, 0x08, 0x1B, 0x31, 0xBF, 0x87, 0x6B, 0x2A, 0x1B, 0xC9, 0xDF, 0x50, 0x95, 0x2D, 0x13, 0xB6, 0xC1, 0x32, 0x1B, 0x11, 0x11, 0x17, 0x21, 0x45, 0xA6, + 0x27, 0xAE, 0x0B, 0x44, 0x27, 0xB9, 0x89, 0x75, 0xCB, 0xFF, 0xF7, 0xD6, 0x82, 0x75, 0x75, 0x4B, 0x45, 0xB6, 0x82, 0xD7, 0x09, 0xE1, 0x68, 0x52, 0x2E, 0x84, 0xFE, 0xA7, 0xDD, 0x3B, 0xB0, 0xF4, + 0x15, 0x05, 0xFF, 0x71, 0x92, 0x64, 0x31, 0xD1, 0xA9, 0x0D, 0x4C, 0xBF, 0x9A, 0x52, 0x7A, 0xD4, 0xE2, 0x84, 0x97, 0x6F, 0xFF, 0x8B, 0xD9, 0xD6, 0x22, 0x4A, 0x4F, 0x26, 0x03, 0x91, 0xA9, 0x87, + 0xFB, 0x6D, 0xA6, 0xEE, 0x42, 0xC2, 0xA4, 0x90, 0x0F, 0x40, 0x7C, 0xE1, 0xF0, 0x2E, 0x32, 0x24, 0x75, 0xD3, 0x13, 0xFB, 0xEB, 0xB6, 0x8C, 0x2E, 0x05, 0x73, 0x08, 0x09, 0x44, 0x8A, 0x74, 0x28, + 0xA5, 0x94, 0x01, 0x39, 0xEB, 0xDF, 0x1B, 0x55, 0x56, 0xFC, 0xC5, 0xD4, 0x2E, 0x1A, 0x13, 0xF3, 0x22, 0x30, 0xCB, 0x6F, 0x07, 0x24, 0x83, 0x1D, 0x0D, 0x07, 0x1B, 0xBA, 0x5A, 0x67, 0x04, 0x80, + 0x6F, 0x47, 0x5B, 0x74, 0xBA, 0x91, 0xB6, 0xE3, 0x85, 0xD4, 0x86, 0x20, 0x95, 0x8D, 0x0A, 0xB1, 0xBF, 0x2B, 0x18, 0x4E, 0x10, 0xF3, 0xE7, 0x53, 0xB7, 0x13, 0x37, 0xBE, 0x9E, 0xB6, 0x53, 0x78, + 0x67, 0x85, 0xB4, 0x3A, 0xC7, 0xE5, 0xC4, 0x94, 0xAC, 0x1B, 0xCB, 0x04, 0x3D, 0x46, 0x14, 0x25, 0xB3, 0x60, 0x98, 0xAC, 0x93, 0x05, 0x5A, 0x01, 0x05, 0xAB, 0x85, 0x23, 0xB6, 0x1D, 0x02, 0x4A, + 0x6E, 0x9B, 0x56, 0xA4, 0x2D, 0x3C, 0x04, 0x72, 0x65, 0x12, 0xAE, 0x4C, 0xFE, 0x05, 0x71, 0x04, 0x46, 0xB0, 0x6F, 0x69, 0x42, 0x34, 0xEE, 0x4F, 0xA8, 0xFE, 0xED, 0xDD, 0xC5, 0xF2, 0x8A, 0x65, + 0xED, 0xE2, 0xEB, 0x58, 0xE9, 0x65, 0xFE, 0x36, 0x27, 0xA5, 0x71, 0xBC, 0x45, 0xB3, 0x97, 0xED, 0x09, 0x2A, 0xB4, 0xBE, 0x00, 0x04, 0x17, 0x29, 0xC4, 0xD1, 0x92, 0xFE, 0x30, 0x67, 0x82, 0x79, + 0xD2, 0x23, 0xA8, 0x48, 0xCF, 0x43, 0x66, 0xE9, 0x2B, 0x3F, 0x68, 0xDE, 0xE9, 0x7C, 0x9B, 0x4A, 0x7F, 0xF2, 0x2F, 0x93, 0x7B, 0xE6, 0xC5, 0x66, 0x39, 0x96, 0x1D, 0xB2, 0x9F, 0xA3, 0xCF, 0xEC, + 0xFF, 0xF2, 0x93, 0x14, 0x08, 0x86, 0xFF, 0xB9, 0x2E, 0xBC, 0x79, 0xDA, 0xB5, 0x9C, 0xEA, 0xF8, 0x69, 0xC6, 0x4F, 0x8E, 0xAF, 0x58, 0x5C, 0xE9, 0x7D, 0xD6, 0xB7, 0x8F, 0x89, 0x27, 0x72, 0xDB, + 0x88, 0xA9, 0x58, 0xCF, 0x0A, 0xB5, 0x57, 0xA7, 0xFA, 0xA8, 0x3F, 0xE6, 0x21, 0x47, 0x7E, 0x2B, 0x84, 0x49, 0x7A, 0xB5, 0xA8, 0xEC, 0xF4, 0xA7, 0xBD, 0x32, 0xDF, 0xB9, 0x02, 0xF0, 0x5D, 0x2C, + 0xA3, 0x10, 0x47, 0xD0, 0xF1, 0x91, 0x9A, 0xDD, 0xE1, 0xEE, 0x6D, 0xFD, 0x58, 0xE5, 0x9B, 0xC4, 0xDA, 0xB3, 0xCC, 0xBB, 0xA3, 0x6A, 0xAA, 0xF6, 0xAF, 0xCC, 0xC7, 0xB0, 0x95, 0xCA, 0x94, 0xA1, + 0x95, 0xBE, 0x9A, 0x28, 0x95, 0x26, 0xB5, 0x88, 0xC3, 0xA9, 0xC5, 0x68, 0x76, 0xFC, 0x41, 0x5D, 0x52, 0x1D, 0x44, 0x2B, 0xAC, 0x02, 0x98, 0xD3, 0x02, 0x41, 0x9A, 0xD5, 0x27, 0xDA, 0x24, 0x9C, + 0x2A, 0x66, 0x0C, 0xD0, 0x64, 0x21, 0x3F, 0xFA, 0xD5, 0x63, 0x18, 0x3F, 0x37, 0x97, 0x25, 0x78, 0xEE, 0xB9, 0xF7, 0x0A, 0xC6, 0x7A, 0xEE, 0x6C, 0xC2, 0xB7, 0x1F, 0x28, 0x3A, 0x95, 0x93, 0x0B, + 0x55, 0x47, 0x38, 0x55, 0x57, 0x91, 0xC2, 0x5E, 0x7A, 0x39, 0x9E, 0x68, 0x56, 0x36, 0xD5, 0x8D, 0x69, 0xCB, 0x6B, 0xE7, 0x93, 0xB4, 0x5C, 0x19, 0x69, 0xE7, 0xD5, 0x61, 0x56, 0x27, 0xEB, 0xC3, + 0x2E, 0xED, 0x45, 0x44, 0x0F, 0x87, 0x88, 0x0D, 0x28, 0x29, 0xFA, 0x4F, 0xC8, 0x71, 0x86, 0x61, 0x64, 0xD2, 0x59, 0xED, 0x95, 0xD2, 0x73, 0x18, 0x71, 0x01, 0x7F, 0xF5, 0x18, 0x94, 0x06, 0x6F, + 0xAE, 0x1F, 0xFA, 0x6F, 0x4B, 0x4A, 0x6F, 0x84, 0xFC, 0xFF, 0xDA, 0x09, 0xE7, 0x18, 0xFA, 0x17, 0x13, 0x5E, 0xDB, 0x3F, 0x48, 0x55, 0x8D, 0x5B, 0xA6, 0x7F, 0x9E, 0x6F, 0x09, 0x00, 0x34, 0x0B, + 0xD0, 0x4D, 0xFE, 0x59, 0xB7, 0xBD, 0x67, 0x74, 0x58, 0x84, 0xFB, 0x84, 0xAE, 0x3F, 0x8E, 0xE7, 0x63, 0xD2, 0x02, 0x74, 0x36, 0x52, 0xD4, 0xF7, 0x33, 0x34, 0x50, 0x58, 0x04, 0x90, 0xB9, 0xC7, + 0x44, 0x93, 0x5B, 0x19, 0xC1, 0xD5, 0xFB, 0x0D, 0xB5, 0xFB, 0xB4, 0x61, 0x41, 0x13, 0x62, 0x83, 0x80, 0x37, 0xEB, 0x7E, 0xC3, 0xF6, 0x3F, 0x26, 0xC8, 0x93, 0xE7, 0xCC, 0x1C, 0x3B, 0x3F, 0x47, + 0x67, 0xAB, 0xAE, 0x00, 0xFE, 0xB7, 0xBB, 0x99, 0xB1, 0x42, 0x0B, 0xB2, 0x9E, 0xA6, 0x14, 0x74, 0x78, 0x96, 0xD9, 0xED, 0xCF, 0x81, 0x07, 0xFE, 0x50, 0x4C, 0x9C, 0x30, 0x8A, 0x82, 0x64, 0xDA, + 0xCE, 0x31, 0x8D, 0x87, 0xCF, 0xE4, 0x76, 0x18, 0x03, 0xE9, 0xA6, 0x0D, 0xEF, 0xA6, 0x14, 0x4A, 0xAB, 0xC1, 0xF1, 0x0A, 0x45, 0xB1, 0x40, 0xDE, 0xD7, 0x54, 0xE7, 0x35, 0x86, 0xC4, 0x67, 0xBB, + 0x7B, 0xF1, 0x9E, 0xDE, 0xF2, 0x5B, 0xE0, 0xC6, 0x5E, 0x93, 0xC5, 0xE5, 0xEB, 0x8F, 0x88, 0x0C, 0xCE, 0x4A, 0x85, 0x87, 0x57, 0xF8, 0xFF, 0x56, 0x06, 0x2B, 0x10, 0x67, 0xF4, 0x10, 0x6F, 0x76, + 0xB7, 0x00, 0x7F, 0x6E, 0xA6, 0xF9, 0x45, 0x04, 0x7E, 0x85, 0xBD, 0x0F, 0xAD, 0x9D, 0x26, 0x99, 0x4F, 0x67, 0x8A, 0x06, 0x12, 0xB8, 0x7C, 0xCF, 0x9C, 0x0C, 0xF9, 0xA4, 0x33, 0xD8, 0x89, 0xC9, + 0x6E, 0x4C, 0x12, 0xBE, 0x37, 0x22, 0x77, 0x00, 0x5B, 0x06, 0xAD, 0x12, 0x71, 0x05, 0xD1, 0x6D, 0x8F, 0xB1, 0x42, 0xAE, 0xAE, 0x53, 0x73, 0xAB, 0xD6, 0x1D, 0x9A, 0xDC, 0xFC, 0x55, 0x50, 0xD6, + 0x23, 0xCA, 0x3B, 0x88, 0x24, 0xB0, 0xE2, 0xE0, 0x8C, 0x2B, 0xF4, 0xE2, 0x84, 0x1E, 0xAC, 0x4C, 0x5D, 0xC5, 0x6C, 0xF8, 0x95, 0x4C, 0xF2, 0x07, 0xC2, 0x63, 0xF2, 0x7C, 0x9F, 0x30, 0x9F, 0x10, + 0x30, 0x7C, 0x0D, 0x84, 0xA6, 0x58, 0x78, 0x42, 0x50, 0x31, 0x37, 0x5D, 0xD8, 0x10, 0xD2, 0xD7, 0xE5, 0x10, 0x98, 0xA3, 0x81, 0x43, 0x50, 0x79, 0x5C, 0x4A, 0x07, 0x7F, 0xA4, 0x0D, 0xD4, 0x4F, + 0x0F, 0xA7, 0x51, 0x0F, 0x7C, 0x3F, 0x63, 0x14, 0x07, 0xCF, 0x34, 0xF6, 0x04, 0xC7, 0xB3, 0x35, 0x63, 0x2A, 0x20, 0xD2, 0xAD, 0x41, 0x9B, 0xD7, 0xCC, 0x6D, 0x42, 0x42, 0xB1, 0xC6, 0x6C, 0x35, + 0xE5, 0xA5, 0xED, 0xCC, 0xB1, 0x3C, 0xA3, 0x7D, 0x3B, 0x50, 0x46, 0x5F, 0x3B, 0x4A, 0xAF, 0xF7, 0xE3, 0x16, 0x1E, 0x79, 0x36, 0x08, 0x8A, 0xE0, 0x84, 0x01, 0xFD, 0x2C, 0x37, 0xD6, 0x7A, 0x2F, + 0xF9, 0x1D, 0x3E, 0x6F, 0x08, 0x68, 0x6D, 0x64, 0xBC, 0x2F, 0xC6, 0xC5, 0x71, 0x06, 0xE4, 0x9F, 0xA3, 0x84, 0xAC, 0x22, 0x21, 0x9F, 0x07, 0xEE, 0x89, 0x96, 0xCA, 0x3D, 0xFF, 0x59, 0xDC, 0xC5, + 0x09, 0x2A, 0x4B, 0xAD, 0xBE, 0x87, 0xAE, 0xDE, 0x7F, 0x69, 0xA0, 0x4C, 0x79, 0xB3, 0x3B, 0xDF, 0x35, 0xD4, 0xA0, 0xE4, 0xCB, 0x4B, 0x55, 0x01, 0x9C, 0xB0, 0xBF, 0x27, 0x52, 0x95, 0xB9, 0x3B, + 0xDA, 0xBE, 0xA5, 0x16, 0xCA, 0x2B, 0x61, 0x6A, 0x56, 0x91, 0x86, 0x00, 0xB7, 0x24, 0xBE, 0x7A, 0x01, 0xEC, 0x4E, 0xF5, 0x43, 0x12, 0xB3, 0x0D, 0x66, 0xF5, 0x07, 0x81, 0x5F, 0x27, 0x80, 0xFF, + 0xEE, 0x7C, 0x30, 0xF8, 0x42, 0x5A, 0x92, 0x25, 0x2C, 0xE5, 0x50, 0xFA, 0xB4, 0xE9, 0x02, 0xE7, 0xB3, 0x82, 0xD4, 0x6D, 0xBD, 0x20, 0xEF, 0xE1, 0xBB, 0x0E, 0xF8, 0xA4, 0x96, 0x87, 0x3C, 0x09, + 0xC4, 0xCE, 0xB0, 0x30, 0x3C, 0x7F, 0x1D, 0xAB, 0xA0, 0x10, 0x2D, 0xE9, 0x41, 0x90, 0xB6, 0xAC, 0x6D, 0xC8, 0x10, 0xF7, 0x2B, 0xCA, 0x3A, 0xA2, 0x92, 0xFF, 0x38, 0xBD, 0x51, 0xA7, 0xFA, 0xB8, + 0x50, 0x9E, 0xC4, 0xFB, 0xE0, 0xEA, 0xA3, 0xC9, 0x86, 0x16, 0x6A, 0x67, 0x4B, 0x78, 0x71, 0x15, 0x5C, 0x34, 0x8C, 0x47, 0x7E, 0xF8, 0xCE, 0xDC, 0x83, 0x2B, 0x5A, 0xBE, 0xE7, 0x1A, 0x8D, 0x18, + 0xD0, 0x6D, 0xD0, 0xF5, 0x22, 0x11, 0x60, 0xAB, 0xEB, 0x71, 0xE6, 0xE8, 0x2C, 0xFA, 0xBF, 0x73, 0x1E, 0xA3, 0x51, 0x5A, 0x76, 0xEF, 0x07, 0xB2, 0xC1, 0x6C, 0x63, 0xB3, 0x7F, 0x7A, 0xB7, 0x3B, + 0x67, 0xF0, 0x05, 0x92, 0x9A, 0x75, 0x3E, 0x45, 0x3B, 0x93, 0x0C, 0x0A, 0xF4, 0x32, 0x27, 0x7F, 0xD7, 0x7D, 0x8A, 0x1E, 0xB8, 0x02, 0x2C, 0xDE, 0x96, 0x65, 0x76, 0x3B, 0x01, 0x4F, 0x0A, 0x67, + 0x2A, 0x04, 0x16, 0x0B, 0x0A, 0x06, 0xF5, 0x54, 0x0F, 0x4C, 0x26, 0x4B, 0x7F, 0x22, 0x74, 0x06, 0x90, 0xA2, 0x35, 0x2D, 0xC8, 0x63, 0xB5, 0x88, 0x30, 0x3A, 0xD5, 0x1F, 0x0A, 0xE1, 0x62, 0xBF, + 0x79, 0x79, 0x7F, 0x07, 0xB5, 0x34, 0x50, 0x1C, 0xBB, 0xFD, 0xB7, 0x13, 0xA7, 0x24, 0xAA, 0x98, 0xE1, 0x95, 0x32, 0x18, 0x71, 0x80, 0xCC, 0xFA, 0xDC, 0x6E, 0xBE, 0x31, 0x42, 0xFA, 0x7D, 0xB6, + 0x6C, 0xD4, 0xDE, 0x7B, 0x9F, 0xBD, 0x4C, 0x82, 0x35, 0x68, 0x6D, 0xB6, 0x8C, 0xAF, 0x48, 0x9A, 0xFA, 0x4E, 0x1E, 0x87, 0xAE, 0xF0, 0xCE, 0xFD, 0x80, 0x37, 0xE3, 0xA5, 0x78, 0xEE, 0x62, 0xEB, + 0x7F, 0x94, 0xED, 0x5B, 0xC0, 0xB5, 0x8E, 0xEA, 0x4B, 0x4C, 0x45, 0xFC, 0x56, 0xD3, 0x1D, 0x29, 0x94, 0x4D, 0x09, 0x5A, 0xC9, 0x6C, 0x29, 0x08, 0x3D, 0xA2, 0xC7, 0x71, 0x81, 0xD9, 0x7A, 0x55, + 0xFE, 0x6E, 0x90, 0x3A, 0x2F, 0x27, 0x83, 0xDE, 0x0B, 0xAA, 0x5F, 0x47, 0xD7, 0x04, 0x78, 0x5C, 0x33, 0xE8, 0xD5, 0xC8, 0x7E, 0xD6, 0x1E, 0x65, 0x45, 0x91, 0x67, 0x31, 0x0E, 0xB7, 0xA9, 0x95, + 0x74, 0xEF, 0x81, 0x9A, 0xE9, 0x16, 0x1A, 0x3B, 0xD0, 0x96, 0x34, 0x80, 0x3D, 0x9E, 0x1E, 0x4E, 0xC7, 0x38, 0x6D, 0x79, 0x46, 0x98, 0x45, 0x17, 0x21, 0x3A, 0xB9, 0xCF, 0x66, 0xAE, 0xA5, 0x51, + 0xCC, 0x45, 0x7C, 0x39, 0xF8, 0x6A, 0xF2, 0x94, 0xCF, 0x7B, 0x07, 0x3F, 0x56, 0x3E, 0xD4, 0xDA, 0xB9, 0x41, 0x9B, 0xDF, 0x00, 0x4B, 0xD0, 0x5C, 0x92, 0xB4, 0xE8, 0x0E, 0xC3, 0xCF, 0xEA, 0xC9, + 0x7E, 0x1D, 0xDA, 0x55, 0x4F, 0xDA, 0x62, 0x5C, 0x4B, 0x9B, 0x03, 0x9B, 0xAA, 0x7C, 0x5A, 0x2F, 0x6F, 0x97, 0x05, 0x77, 0x92, 0x48, 0x3C, 0xF5, 0xF8, 0x52, 0xD4, 0xC3, 0xAC, 0x71, 0xAD, 0x50, + 0xF7, 0x79, 0x95, 0x3D, 0xCF, 0xE2, 0xF6, 0x3E, 0xD2, 0x35, 0xD8, 0xE1, 0xD5, 0x34, 0x5D, 0x6C, 0x6D, 0xF0, 0x55, 0x5C, 0xC2, 0x63, 0x1D, 0xEA, 0xD9, 0xB7, 0x14, 0xBC, 0x4C, 0x16, 0x50, 0x1E, + 0x01, 0x26, 0x13, 0x81, 0xF3, 0x67, 0x97, 0x15, 0x34, 0x51, 0x23, 0x38, 0x8C, 0x85, 0x2D, 0x57, 0xDC, 0xF1, 0x94, 0x1D, 0x09, 0x11, 0xD4, 0x9F, 0xEA, 0x71, 0x43, 0xFD, 0x2F, 0xC3, 0x43, 0xA5, + 0x07, 0x5B, 0x64, 0xCC, 0xA4, 0x82, 0x91, 0xDC, 0x28, 0xB8, 0x3F, 0x76, 0x07, 0x45, 0x89, 0xEA, 0xB2, 0x17, 0xC7, 0x84, 0x78, 0x40, 0x65, 0x2C, 0x0E, 0x3A, 0xE2, 0x78, 0xB3, 0xB6, 0xFB, 0x0D, + 0x80, 0x0C, 0x5E, 0x7D, 0xB7, 0x9D, 0x5C, 0xB9, 0xCC, 0x1A, 0x87, 0x45, 0x0C, 0x00, 0xB7, 0x67, 0x78, 0x12, 0xD2, 0x2E, 0xE2, 0x0F, 0xDE, 0x8C, 0x17, 0x53, 0xA7, 0xFB, 0x93, 0xBA, 0x8B, 0xBB, + 0x85, 0x95, 0xA6, 0x39, 0x3D, 0xF5, 0x4A, 0xA9, 0xCD, 0xB6, 0xE0, 0x87, 0x9A, 0x26, 0xE4, 0x9B, 0xD3, 0xB0, 0x15, 0x13, 0xC6, 0x05, 0x3A, 0x07, 0x46, 0xC8, 0x59, 0x6C, 0xE5, 0xE5, 0xB2, 0x25, + 0xCF, 0xCA, 0x26, 0xAB, 0x8B, 0xF1, 0x2F, 0x1F, 0xE0, 0xA6, 0x47, 0xA9, 0xE4, 0x45, 0x30, 0x39, 0xA1, 0x22, 0x61, 0x94, 0xC4, 0x6E, 0x8B, 0x98, 0xAC, 0xD7, 0x10, 0xF1, 0x8F, 0xB7, 0xEC, 0x05, + 0x47, 0x6C, 0x1C, 0xD8, 0xFC, 0x31, 0x12, 0xCC, 0xDD, 0xB1, 0x58, 0x2B, 0x88, 0x17, 0xC1, 0x8F, 0xE3, 0x15, 0x35, 0x3E, 0x7A, 0x47, 0xC8, 0x21, 0xE9, 0xEE, 0x3A, 0x43, 0xCA, 0xDE, 0x1B, 0x80, + 0xD9, 0x2A, 0x0A, 0xE8, 0xDC, 0xEB, 0x4D, 0xFF, 0x76, 0x6A, 0x54, 0xDF, 0x36, 0x65, 0xFE, 0xFE, 0x3C, 0x25, 0x2B, 0x72, 0xDA, 0xD7, 0xB1, 0xE3, 0x35, 0x9E, 0x7F, 0xA2, 0x55, 0x62, 0xC3, 0xE3, + 0x9D, 0xB5, 0x21, 0xCE, 0x18, 0x74, 0x11, 0x1F, 0xB0, 0x90, 0xDB, 0xD3, 0x8B, 0x31, 0x80, 0xAD, 0x03, 0x4B, 0x57, 0xB0, 0x31, 0xDC, 0x4D, 0xD6, 0xAF, 0x7C, 0x1A, 0x8A, 0xF3, 0xF6, 0xCE, 0x7E, + 0xDB, 0x1A, 0x9E, 0x4B, 0x6D, 0x4A, 0x59, 0x20, 0xE3, 0x62, 0x08, 0x18, 0x82, 0x06, 0x59, 0x76, 0x2E, 0xF7, 0xA4, 0x24, 0x3F, 0x51, 0xDF, 0x2D, 0x8A, 0x90, 0x07, 0x37, 0xD5, 0x81, 0x05, 0x69, + 0x9B, 0x4E, 0x10, 0xCB, 0xCB, 0x35, 0x9C, 0x7F, 0x3A, 0x40, 0x07, 0x69, 0x7C, 0x48, 0x20, 0x50, 0xEC, 0x33, 0xCF, 0x80, 0x41, 0x91, 0x6A, 0x3B, 0x91, 0x9A, 0x50, 0xD9, 0x6E, 0xF0, 0xF5, 0x89, + 0xFD, 0x45, 0x56, 0xF3, 0x0D, 0xBD, 0xD9, 0x42, 0xEA, 0xB7, 0x9D, 0xFA, 0x97, 0xC0, 0x7E, 0x30, 0x24, 0x70, 0x74, 0x35, 0x2E, 0x1B, 0xF9, 0x8E, 0x34, 0x9C, 0xC7, 0xEF, 0xA5, 0xA1, 0xB8, 0xFC, + 0xE4, 0xF1, 0x8F, 0x1F, 0xAF, 0x6F, 0x07, 0xC9, 0x9C, 0x32, 0x14, 0x48, 0xB0, 0x39, 0x5C, 0x8A, 0x9C, 0xBC, 0x46, 0x64, 0x12, 0xF8, 0x9C, 0x1A, 0x98, 0xBF, 0x57, 0x15, 0x84, 0x28, 0x44, 0xF0, + 0xE8, 0x23, 0x6F, 0xA4, 0x69, 0x6C, 0x46, 0x58, 0xB8, 0xFD, 0xE4, 0x42, 0x5D, 0x09, 0xD6, 0x7A, 0x38, 0xAC, 0x72, 0x58, 0xE5, 0xD5, 0x96, 0x6F, 0x2D, 0x3F, 0xF6, 0x6A, 0x0C, 0x0C, 0xE7, 0x6E, + 0x7F, 0x6B, 0x81, 0xA1, 0xBC, 0xD0, 0x47, 0xFD, 0x3A, 0x20, 0x5B, 0xF0, 0xCC, 0xAE, 0xA3, 0xB1, 0x10, 0x79, 0x90, 0x9C, 0x6C, 0xE5, 0x69, 0x8F, 0x32, 0xE1, 0xF3, 0x40, 0x96, 0x58, 0xFF, 0xA0, + 0x1E, 0xAE, 0xCB, 0x4A, 0xE2, 0xB0, 0x92, 0xB7, 0x89, 0x89, 0xDA, 0xAD, 0x66, 0x23, 0xBB, 0x11, 0xF4, 0x9F, 0x0F, 0x8F, 0x86, 0x99, 0xEC, 0x05, 0x66, 0x15, 0x02, 0xFF, 0xCA, 0xD0, 0x3C, 0xF4, + 0x15, 0x19, 0x1A, 0x22, 0x2D, 0x3C, 0x4C, 0x7B, 0x8A, 0xB0, 0xB5, 0xB9, 0xBB, 0xC2, 0xD9, 0xDC, 0xEF, 0xF7, 0x20, 0x2D, 0x3F, 0x42, 0x44, 0x49, 0x4F, 0x52, 0x53, 0x64, 0x66, 0x69, 0x74, 0xC4, + 0xD9, 0xE6, 0xF5, 0xFA, 0x00, 0x01, 0x04, 0x19, 0x27, 0x37, 0x3D, 0x5A, 0x76, 0x80, 0xB8, 0xC1, 0xC9, 0xFE, 0x20, 0x29, 0x38, 0x3B, 0x3C, 0x48, 0x4D, 0x56, 0x5F, 0x65, 0x79, 0x9D, 0x9E, 0xA6, + 0xA9, 0xAD, 0xD2, 0xDE, 0xE5, 0xE7, 0xF7, 0xF9, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x12, 0x24, 0x32, 0x48, + }, + }, + { + .name = "Dilithium Round 3, Level 3 (4-4) KAT 0", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_44, + .rho_len = 32, + .rho = { + 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, 0x38, 0xD5, 0x06, 0xD8, 0x5B, 0xEF, + }, + .seed_len = 32, + .seed = { + 0x39, 0x4D, 0x16, 0x95, 0x05, 0x9D, 0xFF, 0x40, 0xAE, 0x25, 0x6C, 0x5D, 0x5E, 0xDA, 0xBF, 0xB6, 0x9F, 0x5F, 0x40, 0xF3, 0x7A, 0x58, 0x8F, 0x50, 0x53, 0x2C, 0xA4, 0x08, 0xA8, 0x16, 0x8A, 0xB1, + }, + .tr_len = 32, + .tr = { + 0x87, 0xD0, 0xAD, 0x11, 0x52, 0x21, 0x10, 0x93, 0x14, 0x94, 0xBF, 0x2C, 0xAE, 0xAE, 0x36, 0x97, 0x97, 0x11, 0xBC, 0x58, 0x5B, 0x32, 0xF0, 0x8C, 0x78, 0x49, 0x6F, 0x37, 0x9D, 0x60, 0x4D, 0x53, + }, + .s1_len = 384, + .s1 = { + 0xC0, 0xA6, 0x71, 0x1A, 0x96, 0x6C, 0x11, 0x31, 0x2A, 0xD9, 0xA8, 0x21, 0xD8, 0x08, 0x65, 0x42, 0xA6, 0x00, 0xA4, 0xB4, 0x2C, 0x19, 0x40, 0x72, 0x02, 0x42, 0x62, 0x81, 0x06, 0x21, 0x0A, 0x43, + 0x85, 0x23, 0x31, 0x70, 0x93, 0x08, 0x10, 0x8B, 0x18, 0x8C, 0x02, 0x24, 0x92, 0xC1, 0xB2, 0x84, 0x12, 0xC4, 0x21, 0x8B, 0x04, 0x21, 0x81, 0xC8, 0x61, 0x02, 0x48, 0x05, 0x9C, 0x92, 0x01, 0xC0, + 0x34, 0x88, 0x19, 0x32, 0x6C, 0x58, 0x20, 0x46, 0x89, 0x18, 0x68, 0xA2, 0xC2, 0x8D, 0x82, 0x34, 0x6A, 0x1C, 0x09, 0x42, 0x00, 0xA2, 0x8C, 0xE3, 0xA6, 0x49, 0x1C, 0x11, 0x2C, 0xC2, 0x48, 0x12, + 0xE0, 0x90, 0x21, 0x91, 0x98, 0x50, 0x62, 0xC0, 0x84, 0x62, 0x24, 0x51, 0xCA, 0x06, 0x2C, 0x64, 0x24, 0x0E, 0x1B, 0xB3, 0x31, 0x24, 0x96, 0x85, 0x4B, 0x46, 0x06, 0xDB, 0x26, 0x68, 0xC3, 0x82, + 0x68, 0x44, 0x10, 0x46, 0xC9, 0xB6, 0x21, 0x14, 0x04, 0x81, 0x14, 0x45, 0x50, 0x24, 0x42, 0x08, 0x44, 0x22, 0x71, 0x0B, 0x92, 0x45, 0x9A, 0xA0, 0x81, 0x1A, 0x91, 0x70, 0x9C, 0x24, 0x10, 0x03, + 0x95, 0x70, 0x04, 0xC5, 0x04, 0xC8, 0x26, 0x92, 0xD2, 0x92, 0x00, 0xC0, 0xB2, 0x60, 0xC0, 0xA2, 0x68, 0x09, 0x19, 0x0A, 0xA2, 0x30, 0x0E, 0x18, 0x89, 0x69, 0xE0, 0x00, 0x8D, 0xD8, 0x48, 0x62, + 0xDA, 0x14, 0x71, 0x20, 0x18, 0x05, 0x19, 0x07, 0x44, 0x04, 0x12, 0x40, 0x9B, 0x12, 0x40, 0x11, 0x80, 0x10, 0xD1, 0x42, 0x81, 0x99, 0x28, 0x50, 0x8B, 0x10, 0x91, 0x02, 0x24, 0x64, 0xA0, 0x20, + 0x6D, 0x12, 0x46, 0x21, 0x1C, 0x83, 0x8C, 0x1B, 0x47, 0x69, 0x01, 0x06, 0x90, 0xCC, 0x06, 0x24, 0x81, 0x84, 0x69, 0x20, 0x98, 0x2C, 0x24, 0x12, 0x05, 0x21, 0xB1, 0x50, 0x41, 0x36, 0x02, 0x98, + 0x44, 0x6E, 0xD1, 0xA6, 0x31, 0x11, 0x05, 0x6A, 0xD3, 0xA8, 0x40, 0xCA, 0xA8, 0x4C, 0x62, 0xB0, 0x00, 0x03, 0x13, 0x4A, 0x53, 0x34, 0x46, 0x14, 0x19, 0x40, 0x04, 0xC5, 0x4C, 0xE3, 0x06, 0x69, + 0x5A, 0xB0, 0x89, 0x61, 0x16, 0x8E, 0xCB, 0x10, 0x80, 0x8B, 0x16, 0x8E, 0xD9, 0x90, 0x64, 0x0B, 0x94, 0x60, 0x24, 0x83, 0x85, 0x1A, 0xB3, 0x04, 0x54, 0x26, 0x22, 0x51, 0xB8, 0x25, 0x1C, 0x42, + 0x4A, 0x0B, 0x81, 0x48, 0x42, 0xC4, 0x44, 0x5A, 0x10, 0x20, 0x23, 0x80, 0x84, 0x09, 0xB7, 0x25, 0x4C, 0xC6, 0x48, 0x14, 0x85, 0x4D, 0x19, 0x38, 0x0E, 0x60, 0x16, 0x51, 0xD8, 0x32, 0x6A, 0x0A, + 0x91, 0x89, 0x08, 0xC1, 0x70, 0xE0, 0x96, 0x4D, 0x18, 0x46, 0x8C, 0x01, 0x32, 0x8D, 0x91, 0xC4, 0x05, 0x4A, 0x00, 0x61, 0x23, 0x08, 0x68, 0xA2, 0x10, 0x42, 0x10, 0xA8, 0x61, 0x13, 0x06, 0x21, + }, + .s2_len = 384, + .s2 = { + 0x8A, 0x24, 0x8E, 0x62, 0x06, 0x89, 0xC9, 0xB2, 0x45, 0x08, 0x27, 0x84, 0x51, 0x20, 0x0D, 0x98, 0x04, 0x66, 0xDC, 0x42, 0x05, 0x44, 0x24, 0x85, 0x24, 0x26, 0x28, 0x22, 0x21, 0x61, 0x20, 0x16, + 0x09, 0x0B, 0xA6, 0x2C, 0x0A, 0x11, 0x44, 0xE0, 0x92, 0x81, 0x58, 0x48, 0x0D, 0x42, 0x22, 0x10, 0xA0, 0x06, 0x09, 0x8B, 0x24, 0x6E, 0x81, 0x28, 0x8C, 0xC0, 0x24, 0x80, 0x90, 0x30, 0x8D, 0x84, + 0x36, 0x40, 0x4C, 0xA6, 0x84, 0x50, 0x04, 0x24, 0x94, 0xB6, 0x8D, 0xA2, 0x92, 0x6D, 0x18, 0xB3, 0x44, 0xA0, 0x00, 0x85, 0xE3, 0xB8, 0x05, 0x14, 0x05, 0x04, 0xA4, 0xC2, 0x90, 0x84, 0x22, 0x81, + 0xC3, 0x26, 0x2D, 0x0B, 0x20, 0x66, 0xCC, 0x90, 0x31, 0x98, 0x38, 0x28, 0x10, 0x16, 0x6C, 0xC1, 0x34, 0x45, 0xC0, 0x10, 0x22, 0x24, 0xC6, 0x88, 0x03, 0x46, 0x32, 0xD8, 0x40, 0x90, 0x1C, 0x20, + 0x68, 0x04, 0x15, 0x28, 0x9A, 0x18, 0x81, 0x44, 0x98, 0x8D, 0x9C, 0x20, 0x6E, 0x9C, 0x30, 0x2C, 0xC1, 0xB8, 0x20, 0x61, 0x42, 0x21, 0x08, 0x03, 0x10, 0xA0, 0xC2, 0x8C, 0x58, 0x12, 0x85, 0x53, + 0x20, 0x4C, 0x03, 0x30, 0x81, 0x4C, 0xA4, 0x8D, 0x44, 0xC0, 0x8D, 0x51, 0x40, 0x4C, 0x1C, 0xA7, 0x2C, 0x44, 0x08, 0x65, 0xA0, 0x38, 0x40, 0xDA, 0x20, 0x80, 0x81, 0x06, 0x85, 0x8C, 0x26, 0x0D, + 0xE2, 0xA8, 0x8C, 0x9C, 0x44, 0x11, 0x59, 0x42, 0x28, 0xC4, 0x26, 0x04, 0x44, 0x14, 0x26, 0xA1, 0x42, 0x64, 0x08, 0xC0, 0x85, 0x11, 0x01, 0x86, 0x9B, 0x48, 0x31, 0x99, 0xB2, 0x0C, 0x80, 0x46, + 0x44, 0x59, 0xA8, 0x8C, 0x00, 0x42, 0x08, 0x98, 0x82, 0x90, 0x0A, 0xB5, 0x45, 0x62, 0x24, 0x48, 0x12, 0x96, 0x05, 0x44, 0x12, 0x46, 0x00, 0xC8, 0x88, 0x13, 0xA0, 0x61, 0xE1, 0x28, 0x4D, 0x0A, + 0xB9, 0x91, 0x4B, 0x96, 0x20, 0x99, 0xB8, 0x44, 0x00, 0x31, 0x4E, 0x98, 0x12, 0x85, 0x00, 0xB6, 0x01, 0x83, 0xA0, 0x0D, 0x14, 0x15, 0x0E, 0x18, 0x81, 0x10, 0x19, 0x01, 0x22, 0x4A, 0x06, 0x68, + 0x1A, 0x49, 0x8D, 0xE1, 0xA2, 0x84, 0x11, 0xC6, 0x31, 0x21, 0x26, 0x25, 0x91, 0xA0, 0x6D, 0x03, 0x05, 0x24, 0xA1, 0xB6, 0x08, 0x94, 0x44, 0x72, 0x43, 0x34, 0x12, 0x5B, 0xB4, 0x20, 0x41, 0xB6, + 0x50, 0xD0, 0x88, 0x8D, 0x0B, 0x07, 0x4D, 0x1C, 0x94, 0x64, 0x4C, 0x20, 0x8E, 0x8B, 0x88, 0x08, 0xE0, 0x30, 0x09, 0x44, 0x20, 0x05, 0x49, 0x86, 0x4D, 0x03, 0x13, 0x4E, 0x19, 0xC9, 0x84, 0x09, + 0x37, 0x61, 0x1A, 0x43, 0x68, 0x4A, 0x80, 0x90, 0x02, 0x04, 0x31, 0x1C, 0x17, 0x42, 0x18, 0x40, 0x80, 0xC8, 0x30, 0x8E, 0xE1, 0xA2, 0x41, 0xC3, 0x34, 0x04, 0xA3, 0x28, 0x22, 0x51, 0x24, 0x71, + }, + .t0_len = 1664, + .t0 = { + 0x88, 0xD6, 0xFE, 0xF4, 0x67, 0x12, 0xCA, 0x18, 0x28, 0x72, 0xAB, 0x29, 0x19, 0x67, 0x8A, 0xFF, 0x9D, 0x94, 0xE7, 0x43, 0xE0, 0x63, 0xA3, 0x9E, 0x0C, 0x35, 0xCA, 0xF7, 0x2A, 0x7F, 0x2E, 0xDA, + 0x28, 0xE6, 0x58, 0x58, 0x52, 0x0D, 0x5D, 0x84, 0x67, 0xDE, 0x74, 0x7C, 0xF3, 0x40, 0x65, 0x3B, 0x52, 0xC2, 0x68, 0xF5, 0x54, 0x13, 0xF5, 0xAD, 0xDC, 0x7D, 0x49, 0x01, 0x1E, 0xC3, 0x3E, 0xDD, + 0x53, 0x74, 0x23, 0xA8, 0x42, 0x88, 0x86, 0x93, 0x37, 0xAE, 0xA0, 0x78, 0x1A, 0x12, 0x42, 0x69, 0x07, 0x14, 0x51, 0x72, 0x2D, 0xB3, 0xBB, 0x8F, 0x2C, 0xE5, 0xB1, 0x55, 0x2F, 0x83, 0xD2, 0xAF, + 0x07, 0xF2, 0x56, 0x13, 0x91, 0x8A, 0x9F, 0x4E, 0x6F, 0x12, 0x57, 0x60, 0x38, 0x88, 0xE5, 0x89, 0x30, 0x8C, 0xA5, 0xF9, 0x5F, 0x07, 0x14, 0x3D, 0x23, 0xBA, 0xAE, 0x17, 0x52, 0x0B, 0x36, 0xB6, + 0xE0, 0xE9, 0x4F, 0xAF, 0x68, 0x45, 0xEB, 0x21, 0x31, 0xAE, 0xC3, 0x83, 0xE6, 0x3B, 0xC8, 0x64, 0x4E, 0xE5, 0xF1, 0xAC, 0xCB, 0xA8, 0x2F, 0x92, 0x11, 0xE5, 0x7A, 0xFC, 0xBF, 0x50, 0x9C, 0x11, + 0x31, 0xA3, 0x74, 0x66, 0xBC, 0x91, 0xB3, 0x57, 0xDC, 0xBB, 0xBC, 0x14, 0xCC, 0xC3, 0x19, 0xC4, 0xCC, 0x6A, 0xC7, 0x5F, 0xCD, 0xC8, 0x2C, 0x65, 0x96, 0xD0, 0x77, 0x70, 0xC8, 0x27, 0x7A, 0xD3, + 0x70, 0xB1, 0x92, 0xA0, 0xB4, 0xE0, 0x5F, 0x81, 0x2E, 0x0E, 0x26, 0x5D, 0x29, 0x12, 0xAA, 0x29, 0xF0, 0x3F, 0xC9, 0xF7, 0x2D, 0xFA, 0x69, 0xC9, 0xB1, 0x29, 0x1A, 0x3F, 0xC5, 0x83, 0x64, 0x2B, + 0x23, 0x5F, 0x69, 0x91, 0xA9, 0x54, 0x78, 0x83, 0x47, 0xF6, 0x0A, 0x03, 0x28, 0xC4, 0x8E, 0xCE, 0xE5, 0x1B, 0xA0, 0x2D, 0xFF, 0x32, 0x3A, 0xBD, 0x91, 0x16, 0x67, 0xCB, 0x14, 0x54, 0x9B, 0x61, + 0x8F, 0x1C, 0x5D, 0x25, 0x0C, 0xAC, 0x9E, 0x35, 0xE0, 0x71, 0x60, 0x19, 0x92, 0xFB, 0xEC, 0x0B, 0xAE, 0x6F, 0x74, 0x21, 0x30, 0x81, 0x40, 0x47, 0x44, 0xD1, 0x2F, 0x2A, 0x0E, 0x04, 0xBD, 0xB2, + 0x65, 0xE0, 0x92, 0x4C, 0xAD, 0xA4, 0x0D, 0x1F, 0xA1, 0xF3, 0x8A, 0xCA, 0x46, 0x06, 0xBF, 0xD4, 0x57, 0x57, 0x12, 0xB8, 0x26, 0x0A, 0x45, 0x6F, 0xDD, 0xEE, 0xEF, 0xE7, 0xCA, 0x25, 0x9B, 0xCD, + 0xA9, 0x7B, 0x9B, 0x93, 0x9A, 0x5F, 0xD2, 0x88, 0x9C, 0x9B, 0x49, 0xFB, 0x7D, 0x4E, 0x35, 0x53, 0xDE, 0xA6, 0x1B, 0x33, 0x39, 0xBD, 0x0E, 0x6B, 0x16, 0xBF, 0x3B, 0xB2, 0x27, 0x10, 0x3B, 0xF9, + 0x20, 0x2E, 0x72, 0xDC, 0x50, 0x2E, 0x28, 0xF7, 0xCE, 0x15, 0x59, 0xA4, 0x63, 0x1F, 0x37, 0x25, 0x20, 0x32, 0x4E, 0x4E, 0xBA, 0x07, 0x54, 0x5F, 0x78, 0xBF, 0x4D, 0x94, 0xB0, 0xE5, 0xB8, 0xBF, + 0x51, 0xB8, 0xF1, 0x76, 0x53, 0x3D, 0x5C, 0xFE, 0xA5, 0x23, 0x2F, 0x28, 0x3A, 0x47, 0x60, 0x5F, 0xA6, 0x5D, 0xDB, 0x17, 0xC8, 0x91, 0xC2, 0x51, 0x01, 0x1C, 0x4E, 0x98, 0xEE, 0xB6, 0xEB, 0x00, + 0xCB, 0x65, 0xBA, 0x31, 0xC8, 0xF0, 0x25, 0xC8, 0x7A, 0x9F, 0xE0, 0x2D, 0xBC, 0x10, 0xC5, 0xD8, 0x3A, 0x06, 0x5E, 0xBA, 0x5D, 0x7B, 0x2A, 0x19, 0xD5, 0xA1, 0xCB, 0x2C, 0x16, 0x0A, 0xE1, 0x66, + 0xE8, 0x67, 0xF2, 0xAF, 0x8C, 0x7D, 0x49, 0xD6, 0x3F, 0xB8, 0x3A, 0x61, 0x49, 0x57, 0xFC, 0x0A, 0x3B, 0x5A, 0x5C, 0x74, 0x99, 0x0E, 0x9A, 0x2B, 0x02, 0x12, 0x0C, 0x7E, 0x6D, 0xE3, 0x7E, 0x15, + 0x5F, 0xB4, 0x72, 0xF5, 0x0F, 0x0A, 0x45, 0xE4, 0x7C, 0xF5, 0xF9, 0xD7, 0xA4, 0xC8, 0x29, 0x82, 0xC9, 0xDC, 0x86, 0xAE, 0x87, 0x7C, 0x3F, 0xD1, 0x88, 0x59, 0x43, 0xE4, 0x39, 0xFB, 0x00, 0x3C, + 0x7A, 0x9A, 0x42, 0xF7, 0x1B, 0x4F, 0xF6, 0xF0, 0xA2, 0x8B, 0x14, 0x0C, 0xBD, 0xBA, 0x6E, 0x71, 0xB1, 0x3A, 0xC3, 0x1B, 0x23, 0xDE, 0x9E, 0xAB, 0x78, 0x37, 0xE1, 0x5A, 0x69, 0xF8, 0x33, 0xEB, + 0x7B, 0x56, 0xA7, 0x1D, 0x8B, 0xC2, 0xCA, 0xF1, 0xF2, 0xA3, 0x1C, 0x34, 0x5B, 0xD5, 0xF4, 0x6E, 0xE0, 0x13, 0xA7, 0xC6, 0x89, 0x37, 0x23, 0x37, 0x19, 0x1D, 0xAA, 0x80, 0x0C, 0x0A, 0xC6, 0xC4, + 0x6C, 0x9F, 0xF6, 0x88, 0xB1, 0xA0, 0x13, 0x47, 0xF2, 0x57, 0xC4, 0x74, 0xAA, 0x3D, 0x97, 0xC1, 0xD6, 0x3A, 0x8C, 0x00, 0xE0, 0xA3, 0x7B, 0x68, 0x16, 0x73, 0xF5, 0x7C, 0x1C, 0x9C, 0x8F, 0xCC, + 0xD4, 0x6F, 0x17, 0x4C, 0x74, 0xA2, 0x9D, 0x84, 0xCE, 0xB7, 0x1F, 0x7E, 0x6B, 0x2F, 0x8C, 0xD2, 0xB0, 0x89, 0xED, 0x43, 0xF7, 0xC9, 0x6D, 0xAE, 0x81, 0xA2, 0x23, 0x41, 0x8C, 0x20, 0xB1, 0x6F, + 0x1D, 0xF3, 0xD1, 0xA9, 0x78, 0xAE, 0x28, 0xF6, 0xDF, 0x35, 0xEC, 0x55, 0x9D, 0x04, 0xD2, 0x0E, 0xC7, 0x4B, 0x22, 0x4A, 0xEA, 0x31, 0xA2, 0x89, 0xB0, 0x15, 0xB0, 0x69, 0xE9, 0xCB, 0xBB, 0xF7, + 0xCF, 0x6D, 0xE9, 0x4C, 0xFB, 0x2A, 0x96, 0xE4, 0xAE, 0x34, 0x62, 0xC9, 0x60, 0x03, 0xCD, 0xDA, 0x87, 0xDB, 0x56, 0x1A, 0xF2, 0xCE, 0x3C, 0x0B, 0xA1, 0xD9, 0x04, 0x13, 0xFD, 0xCE, 0x3C, 0xCF, + 0x43, 0x90, 0xC0, 0x2C, 0x1C, 0xB9, 0xF6, 0x54, 0xF4, 0x82, 0x0E, 0xC3, 0x30, 0x15, 0x45, 0x7D, 0x4A, 0x62, 0x9F, 0xBF, 0x39, 0x41, 0x9C, 0xAB, 0x76, 0x42, 0xD6, 0x88, 0x5E, 0x10, 0x3F, 0xCE, + 0x0D, 0x42, 0x06, 0xCC, 0xE7, 0xC1, 0x2C, 0x6F, 0xC4, 0x4F, 0xA3, 0x3A, 0xD0, 0x86, 0x4C, 0x33, 0x71, 0xA7, 0xCB, 0xE8, 0x20, 0xE3, 0xB3, 0x71, 0xB6, 0x56, 0xA3, 0x8F, 0x2E, 0x7F, 0xF1, 0x8F, + 0xE4, 0xA5, 0x0C, 0x8A, 0xB3, 0xF8, 0x5D, 0x78, 0x3F, 0xB5, 0x78, 0x35, 0xCE, 0xD8, 0x49, 0x0B, 0x84, 0xEE, 0x0D, 0x99, 0xAF, 0x0D, 0x64, 0xC4, 0x83, 0xCE, 0xB6, 0x36, 0x6F, 0xF5, 0x4F, 0x8A, + 0xC8, 0xA4, 0x0D, 0xB1, 0xAF, 0xA5, 0x73, 0xA4, 0xFB, 0x32, 0x6C, 0x74, 0xF0, 0x23, 0x6E, 0xCE, 0xF3, 0xDA, 0x71, 0x20, 0x66, 0x5C, 0xCE, 0x05, 0xDD, 0x65, 0x4B, 0x50, 0x71, 0x72, 0x3A, 0x83, + 0x48, 0xE7, 0xCD, 0x77, 0x93, 0x51, 0x38, 0x19, 0xB6, 0x1C, 0xB6, 0x4E, 0x13, 0x28, 0xE8, 0xB2, 0x2E, 0x76, 0x64, 0xBD, 0x6B, 0x41, 0xB5, 0x71, 0x0D, 0x19, 0xEA, 0x88, 0x09, 0xD4, 0x45, 0x08, + 0x50, 0xE9, 0x07, 0xDF, 0xC4, 0xD0, 0xB7, 0x5F, 0x58, 0x8C, 0xEC, 0xE9, 0x62, 0xE9, 0xE0, 0x93, 0x7C, 0xE1, 0x40, 0x24, 0x46, 0xA4, 0xD2, 0x89, 0x1A, 0x46, 0xE6, 0x61, 0x7F, 0xB2, 0x9D, 0x4F, + 0xCD, 0x71, 0x26, 0x06, 0xF7, 0x81, 0x9E, 0xCA, 0x60, 0xF7, 0xE0, 0xD5, 0xB1, 0x9E, 0x7F, 0xFB, 0x57, 0xC7, 0x3C, 0x16, 0xFF, 0xEE, 0xB9, 0x00, 0x38, 0x41, 0x0C, 0xB9, 0xFC, 0xBB, 0x5E, 0x9D, + 0x51, 0xEB, 0x3E, 0xB6, 0x29, 0x7E, 0x9F, 0xF6, 0xAB, 0x70, 0x88, 0xFE, 0x2D, 0x9B, 0x23, 0x7B, 0xC2, 0x4C, 0xF7, 0xF8, 0x29, 0x01, 0x18, 0xA5, 0xE0, 0xE0, 0x0A, 0x0B, 0x90, 0x3F, 0xB6, 0x37, + 0x5C, 0x84, 0x81, 0x76, 0xCD, 0x0A, 0x8C, 0x88, 0x75, 0xCC, 0x59, 0x19, 0x9C, 0xDA, 0x11, 0xA8, 0x7A, 0x78, 0xF6, 0x5C, 0xC4, 0x04, 0x33, 0x0B, 0x08, 0x75, 0x71, 0xFD, 0x06, 0x33, 0xE2, 0x71, + 0x29, 0xFD, 0xAB, 0x5A, 0x8A, 0x1F, 0x79, 0x3E, 0x52, 0x41, 0x2B, 0x00, 0x83, 0xFD, 0x5C, 0x74, 0xDB, 0x3C, 0xF6, 0x0C, 0x25, 0x43, 0xCE, 0x7C, 0x91, 0xB2, 0x80, 0x0E, 0x40, 0x20, 0x3F, 0x8D, + 0x99, 0xFE, 0x5F, 0xDE, 0x5B, 0x10, 0x8E, 0x7E, 0xDC, 0x80, 0xEB, 0xB9, 0xBB, 0x34, 0x98, 0x6E, 0xC5, 0xC5, 0xA8, 0xF5, 0x80, 0xE7, 0x57, 0x52, 0x90, 0x7F, 0xF0, 0xF2, 0x94, 0xC8, 0x66, 0xC2, + 0xCF, 0x1F, 0x36, 0x2E, 0x84, 0x0B, 0x68, 0x81, 0xBD, 0x43, 0x21, 0x92, 0x01, 0x78, 0x1C, 0x63, 0xB0, 0x03, 0x9A, 0x95, 0xBC, 0xFB, 0x4A, 0x0F, 0xEC, 0xE5, 0x69, 0xDF, 0x00, 0x52, 0x3C, 0xE9, + 0xC0, 0x84, 0xB0, 0x22, 0xB3, 0xB0, 0x22, 0x24, 0x2E, 0x28, 0x41, 0x97, 0x96, 0xAC, 0xF0, 0xA0, 0xC9, 0x95, 0xF9, 0x48, 0xDB, 0xFF, 0xFD, 0x30, 0xD7, 0x7E, 0xD1, 0x05, 0xA3, 0xC9, 0x94, 0x3C, + 0x40, 0x6B, 0x30, 0x5B, 0xC8, 0x1A, 0x6A, 0x24, 0x8A, 0x29, 0x15, 0x48, 0xF2, 0xA6, 0x7F, 0x43, 0x8D, 0x96, 0x6A, 0x57, 0xD5, 0x3F, 0x4B, 0x7B, 0xE1, 0x53, 0x54, 0xE5, 0x81, 0xBE, 0x16, 0xF7, + 0xAD, 0x64, 0xD1, 0x64, 0xE8, 0x57, 0x87, 0xDF, 0x58, 0x49, 0xC8, 0x10, 0xAF, 0xC2, 0x8D, 0x06, 0x48, 0x2F, 0x44, 0x1B, 0x5F, 0xDE, 0x3D, 0xB2, 0xED, 0x36, 0xDD, 0x25, 0xAA, 0x66, 0x64, 0xD4, + 0xD4, 0x3F, 0xFA, 0x32, 0xED, 0xA2, 0x56, 0x89, 0xC9, 0xF4, 0xA5, 0xD5, 0x14, 0xFC, 0x66, 0x23, 0x1C, 0x54, 0x01, 0x52, 0x09, 0x22, 0x52, 0x44, 0x38, 0xEF, 0x1D, 0xC7, 0x8D, 0x69, 0x3C, 0x97, + 0x18, 0xDE, 0xBB, 0xD2, 0x43, 0x31, 0x26, 0x74, 0xC8, 0x99, 0xF1, 0x89, 0x10, 0xE3, 0x89, 0xC8, 0xEB, 0xE5, 0x05, 0x82, 0x4B, 0xCC, 0x42, 0xCD, 0x4A, 0x9A, 0xCE, 0x19, 0x37, 0x68, 0x22, 0x02, + 0x19, 0x01, 0x1F, 0x3B, 0x1F, 0x33, 0x54, 0x27, 0xBF, 0xF9, 0xE8, 0xBD, 0xED, 0x5C, 0x08, 0x71, 0x1A, 0x09, 0xC2, 0xB7, 0x1C, 0xB9, 0x64, 0xC5, 0x6A, 0x83, 0x93, 0xBF, 0xD2, 0xB5, 0x6E, 0x9B, + 0x6B, 0x2F, 0x51, 0x3E, 0x68, 0x25, 0x87, 0xDC, 0x1B, 0x8E, 0xD1, 0x96, 0x06, 0x63, 0x26, 0x87, 0x10, 0x25, 0x62, 0x80, 0x36, 0x70, 0x00, 0x63, 0x17, 0x6D, 0x34, 0x5D, 0xE3, 0x84, 0xE1, 0x82, + 0xD6, 0xC4, 0x17, 0xA3, 0x2A, 0xB1, 0x10, 0x95, 0xEF, 0x59, 0xBB, 0x4D, 0x17, 0x1B, 0x9C, 0xF8, 0x1D, 0x17, 0xAC, 0x42, 0x66, 0x4D, 0xED, 0x93, 0x3C, 0xCB, 0x72, 0x2C, 0x69, 0x85, 0x7F, 0xFC, + 0x53, 0xC8, 0xE7, 0xF2, 0x47, 0x4B, 0x0C, 0xB2, 0xDF, 0xF2, 0xDD, 0xC8, 0xA5, 0xC6, 0x01, 0xC8, 0x4A, 0x70, 0x19, 0x81, 0x19, 0x9B, 0xCC, 0xF7, 0x41, 0x12, 0xA6, 0xEC, 0x06, 0x2C, 0x4F, 0xEB, + 0x60, 0x1A, 0x02, 0x8A, 0xF0, 0x10, 0x32, 0xAD, 0xB6, 0xBD, 0x15, 0xD4, 0xC2, 0xB9, 0x55, 0x0A, 0xA8, 0x50, 0xAD, 0x62, 0xCC, 0xC3, 0xA3, 0x66, 0x5D, 0x52, 0x12, 0xB1, 0x2E, 0x0F, 0xD5, 0xC5, + 0x32, 0x6A, 0x1E, 0x5E, 0xB1, 0xF1, 0x0D, 0x55, 0x7D, 0x94, 0x60, 0x5E, 0x8E, 0x3F, 0x35, 0x6E, 0x08, 0xFF, 0x7F, 0xD8, 0x84, 0xED, 0x3C, 0x42, 0x05, 0x46, 0x35, 0x94, 0xC9, 0xAF, 0x2F, 0x39, + 0xE4, 0xB1, 0x27, 0x46, 0x95, 0x23, 0x4B, 0x54, 0xEE, 0xCE, 0xD9, 0x3F, 0x46, 0x0E, 0xDF, 0x1A, 0x13, 0xC2, 0xCB, 0x4B, 0x17, 0xD3, 0x22, 0xF6, 0xF7, 0x9F, 0xE1, 0x6F, 0x03, 0x57, 0xC1, 0xC4, + 0x73, 0x98, 0x63, 0xE7, 0x96, 0x79, 0x1F, 0x86, 0x47, 0xFA, 0xBF, 0x73, 0x0A, 0xB0, 0x0E, 0x0D, 0xA5, 0x09, 0x70, 0x6D, 0x94, 0x57, 0x17, 0x40, 0xF6, 0x1F, 0x7B, 0xAF, 0x36, 0x6D, 0x27, 0x74, + 0xC9, 0xB5, 0xB8, 0xC6, 0x1D, 0xD6, 0xBE, 0x98, 0x19, 0xA6, 0x02, 0x8B, 0x26, 0x4B, 0xB2, 0xE4, 0xAE, 0xA5, 0x4B, 0x56, 0xD4, 0xEC, 0xAB, 0x5B, 0x52, 0x8C, 0xE0, 0xC0, 0xC0, 0xCC, 0xDB, 0x73, + 0x02, 0x33, 0x52, 0xCB, 0x00, 0x44, 0x5B, 0xAB, 0x6F, 0x74, 0x67, 0xB4, 0x64, 0x4D, 0x43, 0x61, 0xC4, 0x64, 0xFA, 0xC6, 0xB5, 0xB1, 0x37, 0xD3, 0x23, 0x91, 0x02, 0x1B, 0x47, 0x5F, 0xCB, 0x5F, + 0x31, 0x77, 0x4F, 0xD8, 0xEC, 0xAB, 0xDF, 0x65, 0x47, 0x5F, 0x25, 0x57, 0x4C, 0x65, 0x55, 0x9C, 0xB3, 0x31, 0xF4, 0x1C, 0x0F, 0x49, 0x8B, 0x74, 0xDD, 0x94, 0x1C, 0x34, 0x4C, 0x50, 0xD8, 0xE6, + 0x4F, 0x95, 0x78, 0x71, 0x4A, 0x32, 0x56, 0x1F, 0xAA, 0xCE, 0xAF, 0x78, 0x14, 0x8E, 0x6D, 0xA4, 0xB5, 0x66, 0x82, 0x69, 0x25, 0x71, 0x4B, 0x17, 0x10, 0x8A, 0xFD, 0xD5, 0x46, 0x38, 0x5A, 0x3C, + 0xD4, 0x54, 0xD5, 0xCA, 0xA1, 0x69, 0x60, 0x91, 0x62, 0x82, 0xA4, 0x7C, 0x43, 0x15, 0xCE, 0x23, 0x6B, 0xD9, 0xE3, 0x25, 0x5C, 0x60, 0x4E, 0xBD, 0xC3, 0x97, 0x72, 0xDB, 0x5C, 0xE0, 0xB2, 0x36, + }, + .t1_len = 1280, + .t1 = { + 0x61, 0x77, 0xE3, 0xDE, 0x0D, 0x4F, 0x1E, 0xF5, 0x84, 0x77, 0x35, 0x94, 0x7B, 0x56, 0xD0, 0x8E, 0x84, 0x1D, 0xB2, 0x44, 0x4F, 0xA2, 0xB7, 0x29, 0xAD, 0xEB, 0x14, 0x17, 0xCA, 0x7A, 0xDF, 0x42, + 0xA1, 0x49, 0x0C, 0x5A, 0x09, 0x7F, 0x00, 0x27, 0x60, 0xC1, 0xFC, 0x41, 0x9B, 0xE8, 0x32, 0x5A, 0xAD, 0x01, 0x97, 0xC5, 0x2C, 0xED, 0x80, 0xD3, 0xDF, 0x18, 0xE7, 0x77, 0x42, 0x65, 0xB2, 0x89, + 0x91, 0x2C, 0xEC, 0xA1, 0xBE, 0x3A, 0x90, 0xD8, 0xA4, 0xFD, 0xE6, 0x5C, 0x84, 0xC6, 0x10, 0x86, 0x4E, 0x47, 0xDE, 0xEC, 0xAE, 0x3E, 0xEA, 0x44, 0x30, 0xB9, 0x90, 0x95, 0x59, 0x40, 0x8D, 0x11, + 0xA6, 0xAB, 0xDB, 0x7D, 0xB9, 0x33, 0x6D, 0xF7, 0xF9, 0x6E, 0xAB, 0x48, 0x64, 0xA6, 0x57, 0x97, 0x91, 0x26, 0x5F, 0xA5, 0x6C, 0x34, 0x8C, 0xB7, 0xD2, 0xDD, 0xC9, 0x0E, 0x13, 0x3A, 0x95, 0xC3, + 0xF6, 0xB1, 0x36, 0x01, 0x42, 0x9F, 0x54, 0x08, 0xBD, 0x99, 0x9A, 0xA4, 0x79, 0xC1, 0x01, 0x81, 0x59, 0x55, 0x0E, 0xC5, 0x5A, 0x11, 0x3C, 0x49, 0x3B, 0xE6, 0x48, 0xF4, 0xE0, 0x36, 0xDD, 0x4F, + 0x8C, 0x80, 0x9E, 0x03, 0x6B, 0x4F, 0xBB, 0x91, 0x8C, 0x2C, 0x48, 0x4A, 0xD8, 0xE1, 0x74, 0x7A, 0xE0, 0x55, 0x85, 0xAB, 0x43, 0x3F, 0xDF, 0x46, 0x1A, 0xF0, 0x3C, 0x25, 0xA7, 0x73, 0x70, 0x07, + 0x21, 0xAA, 0x05, 0xF7, 0x37, 0x9F, 0xE7, 0xF5, 0xED, 0x96, 0x17, 0x5D, 0x40, 0x21, 0x07, 0x6E, 0x7F, 0x52, 0xB6, 0x03, 0x08, 0xEF, 0xF5, 0xD4, 0x2B, 0xA6, 0xE0, 0x93, 0xB3, 0xD0, 0x81, 0x5E, + 0xB3, 0x49, 0x66, 0x46, 0xE4, 0x92, 0x30, 0xA9, 0xB3, 0x5C, 0x8D, 0x41, 0x90, 0x0C, 0x2B, 0xB8, 0xD3, 0xB4, 0x46, 0xA2, 0x31, 0x27, 0xF7, 0xE0, 0x96, 0xD8, 0x5A, 0x1C, 0x79, 0x4A, 0xD4, 0xC8, + 0x92, 0x77, 0x90, 0x4F, 0xC6, 0xBF, 0xEC, 0x57, 0xB1, 0xCD, 0xD8, 0x0D, 0xF9, 0x95, 0x50, 0x30, 0xFD, 0xCA, 0x74, 0x1A, 0xFB, 0xDA, 0xC8, 0x27, 0xB1, 0x3C, 0xCD, 0x54, 0x03, 0x58, 0x8A, 0xF4, + 0x64, 0x40, 0x03, 0xC2, 0x26, 0x5D, 0xFA, 0x4D, 0x41, 0x9D, 0xBC, 0xCD, 0x20, 0x64, 0x89, 0x23, 0x86, 0x51, 0x8B, 0xE9, 0xD5, 0x1C, 0x16, 0x49, 0x82, 0x75, 0xEB, 0xEC, 0xF5, 0xCD, 0xC7, 0xA8, + 0x20, 0xF2, 0xC2, 0x93, 0x14, 0xAC, 0x4A, 0x6F, 0x08, 0xB2, 0x25, 0x2A, 0xD3, 0xCF, 0xB1, 0x99, 0xAA, 0x42, 0xFE, 0x0B, 0x4F, 0xB5, 0x71, 0x97, 0x5C, 0x10, 0x20, 0xD9, 0x49, 0xE1, 0x94, 0xEE, + 0x1E, 0xAD, 0x93, 0x7B, 0xFB, 0x55, 0x0B, 0xB3, 0xBA, 0x8E, 0x35, 0x7A, 0x02, 0x9C, 0x29, 0xF0, 0x77, 0x55, 0x46, 0x02, 0xE1, 0xCA, 0x2F, 0x22, 0x89, 0xCB, 0x91, 0x69, 0x94, 0x1C, 0x3A, 0xAF, + 0xDB, 0x8E, 0x58, 0xC7, 0xF2, 0xAC, 0x77, 0x29, 0x1F, 0xB4, 0x14, 0x7C, 0x65, 0xF6, 0xB0, 0x31, 0xD3, 0xEB, 0xA4, 0x2F, 0x2A, 0xCF, 0xD9, 0x44, 0x8A, 0x5B, 0xC2, 0x2B, 0x47, 0x6E, 0x07, 0xCC, + 0xCE, 0xDA, 0x23, 0x06, 0xC5, 0x54, 0xEC, 0x9B, 0x7A, 0xB6, 0x55, 0xF1, 0xD7, 0x31, 0x8C, 0x2B, 0x7E, 0x67, 0xD5, 0xF6, 0x9B, 0xED, 0xF5, 0x60, 0x00, 0xFD, 0xA9, 0x89, 0x86, 0xB5, 0xAB, 0x1B, + 0x3A, 0x22, 0xD8, 0xDF, 0xD6, 0x68, 0x16, 0x97, 0xB2, 0x3A, 0x55, 0xC9, 0x6E, 0x87, 0x10, 0xF3, 0xF9, 0x8C, 0x04, 0x4F, 0xB1, 0x5F, 0x60, 0x63, 0x13, 0xEE, 0x56, 0xC0, 0xF1, 0xF5, 0xCA, 0x0F, + 0x51, 0x2E, 0x08, 0x48, 0x4F, 0xCB, 0x35, 0x8E, 0x6E, 0x52, 0x8F, 0xFA, 0x89, 0xF8, 0xA8, 0x66, 0xCC, 0xFF, 0x3C, 0x0C, 0x58, 0x13, 0x14, 0x7E, 0xC5, 0x9A, 0xF0, 0x47, 0x0C, 0x4A, 0xAD, 0x01, + 0x41, 0xD3, 0x4F, 0x10, 0x1D, 0xA2, 0xE5, 0xE1, 0xBD, 0x52, 0xD0, 0xD4, 0xC9, 0xB1, 0x3B, 0x3E, 0x3D, 0x87, 0xD1, 0x58, 0x61, 0x05, 0x79, 0x67, 0x54, 0xE7, 0x97, 0x8C, 0xA1, 0xC6, 0x8A, 0x7D, + 0x85, 0xDF, 0x11, 0x2B, 0x7A, 0xB9, 0x21, 0xB3, 0x59, 0xA9, 0xF0, 0x3C, 0xBD, 0x27, 0xA7, 0xEA, 0xC8, 0x7A, 0x9A, 0x80, 0xB0, 0xB2, 0x6B, 0x4C, 0x96, 0x57, 0xED, 0x85, 0xAD, 0x7F, 0xA2, 0x61, + 0x6A, 0xB3, 0x45, 0xEB, 0x82, 0x26, 0xF6, 0x9F, 0xC0, 0xF4, 0x81, 0x83, 0xFF, 0x57, 0x4B, 0xCD, 0x76, 0x7B, 0x56, 0x76, 0x41, 0x3A, 0xDB, 0x12, 0xEA, 0x21, 0x50, 0xA0, 0xE9, 0x76, 0x83, 0xEE, + 0x54, 0x24, 0x3C, 0x25, 0xB7, 0xEA, 0x8A, 0x71, 0x86, 0x06, 0xF8, 0x69, 0x93, 0xD8, 0xD0, 0xDA, 0xCE, 0x83, 0x4E, 0xD3, 0x41, 0xEE, 0xB7, 0x24, 0xFE, 0x3D, 0x5F, 0xF0, 0xBC, 0x8B, 0x8A, 0x7B, + 0x81, 0x04, 0xBA, 0x26, 0x9D, 0x34, 0x13, 0x3A, 0x4C, 0xF8, 0x30, 0x0A, 0x2D, 0x68, 0x84, 0x96, 0xB5, 0x9B, 0x6F, 0xCB, 0xC6, 0x1A, 0xE9, 0x60, 0x62, 0xEA, 0x1D, 0x8E, 0x5B, 0x41, 0x0C, 0x56, + 0x71, 0xF4, 0x24, 0x41, 0x7E, 0xD6, 0x93, 0x32, 0x9C, 0xD9, 0x83, 0x00, 0x1F, 0xFC, 0xD1, 0x00, 0x23, 0xD5, 0x98, 0x85, 0x9F, 0xB7, 0xAD, 0x5F, 0xD2, 0x63, 0x54, 0x71, 0x17, 0x10, 0x06, 0x90, + 0xC6, 0xCE, 0x74, 0x38, 0x95, 0x6E, 0x6C, 0xC5, 0x7F, 0x1B, 0x5D, 0xE5, 0x3B, 0xB0, 0xDC, 0x72, 0xCE, 0x9B, 0x6D, 0xEA, 0xA8, 0x57, 0x89, 0x59, 0x9A, 0x70, 0xF0, 0x05, 0x1F, 0x1A, 0x0E, 0x25, + 0xE8, 0x6D, 0x88, 0x8B, 0x00, 0xDF, 0x36, 0xBD, 0xBC, 0x93, 0xEF, 0x72, 0x17, 0xC4, 0x5A, 0xCE, 0x11, 0xC0, 0x79, 0x0D, 0x70, 0xE9, 0x95, 0x3E, 0x5B, 0x41, 0x7B, 0xA2, 0xFD, 0x9A, 0x4C, 0xAF, + 0x82, 0xF1, 0xFC, 0xE6, 0xF4, 0x5F, 0x53, 0xE2, 0x15, 0xB8, 0x35, 0x5E, 0xF6, 0x1D, 0x89, 0x1D, 0xF1, 0xC7, 0x94, 0x23, 0x1C, 0x16, 0x2D, 0xD2, 0x41, 0x64, 0xB5, 0x34, 0xA9, 0xD4, 0x84, 0x67, + 0xCD, 0xC3, 0x23, 0x62, 0x4C, 0x2F, 0x95, 0xD4, 0x40, 0x2F, 0xF9, 0xD6, 0x6A, 0xB1, 0x19, 0x1A, 0x81, 0x24, 0x14, 0x4A, 0xFA, 0x35, 0xD4, 0xE3, 0x1D, 0xC8, 0x6C, 0xAA, 0x79, 0x7C, 0x31, 0xF6, + 0x8B, 0x85, 0x85, 0x4C, 0xD9, 0x59, 0xC4, 0xFA, 0xC5, 0xEC, 0x53, 0xB3, 0xB5, 0x6D, 0x37, 0x4B, 0x88, 0x8A, 0x9E, 0x97, 0x9A, 0x65, 0x76, 0xB6, 0x34, 0x5E, 0xC8, 0x52, 0x2C, 0x96, 0x06, 0x99, + 0x02, 0x81, 0xBF, 0x3E, 0xF7, 0xC5, 0x94, 0x5D, 0x10, 0xFD, 0x21, 0xA2, 0xA1, 0xD2, 0xE5, 0x40, 0x4C, 0x5C, 0xF2, 0x12, 0x20, 0x64, 0x13, 0x91, 0xB9, 0x8B, 0xCF, 0x82, 0x53, 0x98, 0x30, 0x5B, + 0x56, 0xE5, 0x8B, 0x61, 0x1F, 0xE5, 0x25, 0x32, 0x03, 0xE3, 0xDF, 0x0D, 0x22, 0x46, 0x6A, 0x73, 0xB3, 0xF0, 0xFB, 0xE4, 0x3B, 0x9A, 0x62, 0x92, 0x80, 0x91, 0x89, 0x8B, 0x8A, 0x0E, 0x5B, 0x26, + 0x9D, 0xB5, 0x86, 0xB0, 0xE4, 0xDD, 0xEF, 0x50, 0xD6, 0x82, 0xA1, 0x2D, 0x2C, 0x1B, 0xE8, 0x24, 0x14, 0x9A, 0xA2, 0x54, 0xC6, 0x38, 0x1B, 0xB4, 0x12, 0xD7, 0x7C, 0x3F, 0x9A, 0xA9, 0x02, 0xB6, + 0x88, 0xC8, 0x17, 0x15, 0xA5, 0x9C, 0x83, 0x95, 0x58, 0x55, 0x6D, 0x35, 0xED, 0x4F, 0xC8, 0x3B, 0x4A, 0xB1, 0x81, 0x81, 0xF4, 0x0F, 0x73, 0xDC, 0xD7, 0x68, 0x60, 0xD8, 0xD8, 0xBF, 0x94, 0x52, + 0x02, 0x37, 0xC2, 0xAC, 0x0E, 0x46, 0x3B, 0xA0, 0x9E, 0x3C, 0x97, 0x82, 0x38, 0x0D, 0xC0, 0x7F, 0xE4, 0xFC, 0xBA, 0x34, 0x0C, 0xC2, 0x00, 0x34, 0x39, 0xFD, 0x23, 0x14, 0x61, 0x06, 0x38, 0x07, + 0x0D, 0x6C, 0x9E, 0xEA, 0x0A, 0x70, 0xBA, 0xE8, 0x3B, 0x5D, 0x5D, 0x3C, 0x5D, 0x3F, 0xDE, 0x26, 0xDD, 0x01, 0x60, 0x6C, 0x8C, 0x52, 0x01, 0x58, 0xE7, 0xE5, 0x10, 0x40, 0x20, 0xF2, 0x48, 0xCE, + 0xAA, 0x66, 0x64, 0x57, 0xC1, 0x0A, 0xEB, 0xF0, 0x68, 0xF8, 0xA3, 0xBD, 0x5C, 0xE7, 0xB5, 0x2C, 0x6A, 0xF0, 0xAB, 0xD5, 0x94, 0x4A, 0xF1, 0xAD, 0x47, 0x52, 0xC9, 0x11, 0x39, 0x76, 0x08, 0x3C, + 0x03, 0xB6, 0xC3, 0x4E, 0x1D, 0x47, 0xED, 0x69, 0x64, 0x4C, 0xAD, 0x78, 0x2C, 0x2F, 0x7D, 0x05, 0xF8, 0xA1, 0x48, 0x96, 0x1D, 0x96, 0x5F, 0xA2, 0xE1, 0x72, 0x3A, 0x8D, 0xDE, 0xBC, 0x22, 0xA9, + 0x0C, 0xD7, 0x83, 0xDD, 0x1F, 0x4D, 0xB3, 0x8F, 0xB9, 0xAE, 0x5A, 0x67, 0x14, 0xB3, 0xD9, 0x46, 0x78, 0x16, 0x43, 0xD3, 0x17, 0xB7, 0xDD, 0x79, 0x38, 0x1C, 0xF7, 0x89, 0xA9, 0x58, 0x8B, 0xB3, + 0xE1, 0x93, 0xB9, 0x2A, 0x0B, 0x60, 0xD6, 0xB0, 0x7D, 0x04, 0x7F, 0x69, 0x84, 0xB0, 0x60, 0x9E, 0xC5, 0x75, 0x43, 0xC3, 0x94, 0xCA, 0x8D, 0x5E, 0x5B, 0xCC, 0x2A, 0x73, 0x1A, 0x79, 0x61, 0x8B, + 0xD1, 0xE2, 0xE0, 0xDA, 0x87, 0x04, 0xAF, 0x98, 0xF2, 0x0F, 0x5F, 0x8F, 0x54, 0x52, 0xDD, 0xF6, 0x46, 0xB9, 0x5B, 0x34, 0x1D, 0xD7, 0xF0, 0xD2, 0xCC, 0x1F, 0xA1, 0x5B, 0xD9, 0x89, 0x5C, 0xD5, + 0xB6, 0x5A, 0xA1, 0xCB, 0x94, 0xB5, 0xE2, 0xE7, 0x88, 0xFD, 0xA9, 0x82, 0x5B, 0x65, 0x66, 0x39, 0x19, 0x3D, 0x98, 0x32, 0x81, 0x54, 0xA4, 0xF2, 0xC3, 0x54, 0x95, 0xA3, 0x8B, 0x6E, 0xA0, 0xD2, + 0xFF, 0xAA, 0xA3, 0x5D, 0xF9, 0x2C, 0x20, 0x3C, 0x7F, 0x31, 0xCB, 0xBC, 0xA7, 0xBD, 0x03, 0xC3, 0xC2, 0x30, 0x21, 0x90, 0xCE, 0xCD, 0x16, 0x1F, 0xD4, 0x92, 0x37, 0xE4, 0xF8, 0x39, 0xE3, 0xF3, + }, + .pkcs8_len = 0, + .spki_len = 0, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 2420, + .sig = { + 0xAF, 0x59, 0x20, 0x77, 0x46, 0x03, 0xD2, 0x0E, 0x98, 0xA7, 0x9A, 0xA3, 0xAB, 0xFA, 0x32, 0xB6, 0xE2, 0x25, 0x19, 0xE6, 0x73, 0xE3, 0x7A, 0xC4, 0xAC, 0x73, 0xFE, 0x85, 0x34, 0x1E, 0x2C, 0x29, + 0x23, 0xC1, 0x99, 0x2E, 0x1B, 0x0B, 0xBE, 0x38, 0x73, 0xD7, 0xC8, 0xFC, 0x56, 0x62, 0xF2, 0x07, 0xBF, 0x58, 0xEA, 0x38, 0x1C, 0xD4, 0xA3, 0xA0, 0xC0, 0x62, 0xDE, 0xC4, 0x5B, 0xDA, 0xF8, 0xBA, + 0x0A, 0xA5, 0x2B, 0xEF, 0x6F, 0xA1, 0x4F, 0x3F, 0x6C, 0xF2, 0x8F, 0x76, 0x20, 0xBF, 0x94, 0xA9, 0x2C, 0xC2, 0x7D, 0x04, 0x54, 0x14, 0xA6, 0x4D, 0x65, 0xC0, 0x14, 0x96, 0x30, 0x52, 0x80, 0x24, + 0x28, 0xBF, 0x39, 0x87, 0xA2, 0xD4, 0x75, 0x16, 0xCA, 0x5C, 0x78, 0xAA, 0xB9, 0x6B, 0x7B, 0xE1, 0x1B, 0xCA, 0x5F, 0x2C, 0x5A, 0x26, 0xF3, 0xFC, 0xE3, 0xA2, 0x6E, 0x8E, 0x09, 0xA2, 0x73, 0x8F, + 0x38, 0x6F, 0x75, 0xD4, 0x48, 0xF9, 0x37, 0xEF, 0x19, 0xA8, 0x46, 0xBD, 0x4D, 0xD9, 0x49, 0xCA, 0xAF, 0x36, 0xDB, 0x56, 0x29, 0x88, 0x4A, 0xF5, 0x3A, 0x02, 0x3E, 0x3F, 0x18, 0x0F, 0xE4, 0xC0, + 0xFA, 0xFF, 0x7B, 0xE5, 0xDF, 0xE4, 0xE8, 0x9A, 0xDE, 0x30, 0x95, 0xA6, 0x56, 0x00, 0x42, 0x14, 0x61, 0xAD, 0x08, 0xC1, 0x29, 0xD6, 0xCE, 0xA8, 0x51, 0xBB, 0x39, 0xC0, 0xD7, 0xA7, 0xD1, 0x51, + 0x40, 0x56, 0x89, 0xA0, 0x91, 0xFA, 0x4D, 0xEB, 0xAC, 0x37, 0x3C, 0xF5, 0x4A, 0xE0, 0x78, 0xF0, 0xAF, 0x75, 0x57, 0xBB, 0xC6, 0xF0, 0x6A, 0x53, 0x5A, 0xE8, 0x94, 0x9E, 0x0C, 0x65, 0x30, 0x8A, + 0x59, 0x84, 0x00, 0x72, 0x37, 0x52, 0x95, 0x80, 0x2D, 0x0E, 0x2C, 0xE9, 0xA3, 0xDA, 0x98, 0x42, 0x6A, 0x00, 0xFF, 0x03, 0xFE, 0x80, 0x21, 0x8C, 0x0E, 0xEC, 0x8E, 0xFE, 0x58, 0x1C, 0xB9, 0xCC, + 0x9A, 0x7D, 0x66, 0xB2, 0x06, 0x45, 0xA8, 0xCD, 0x04, 0x90, 0xD3, 0xCE, 0x4F, 0x7E, 0x6F, 0xEA, 0xE9, 0xC9, 0xEB, 0x7A, 0x57, 0xF9, 0x64, 0xD0, 0xEB, 0xC7, 0xC9, 0x0B, 0x7A, 0x9F, 0x86, 0x30, + 0x0B, 0x3E, 0x80, 0x95, 0xE6, 0x4D, 0x12, 0x94, 0xCF, 0xC4, 0xB4, 0xD9, 0xE2, 0x72, 0xE8, 0xFA, 0x8D, 0xB5, 0x70, 0x7D, 0x70, 0x04, 0xAF, 0x22, 0xDB, 0xFF, 0x9C, 0xFD, 0x48, 0x63, 0xDF, 0x57, + 0x3F, 0xE0, 0x04, 0x34, 0x1D, 0xA3, 0xCD, 0x4A, 0x30, 0x82, 0x53, 0x2C, 0x26, 0x20, 0x45, 0x5F, 0xA3, 0x7C, 0x56, 0x2B, 0xAF, 0xD5, 0x68, 0x4E, 0xA1, 0x28, 0xAF, 0xC7, 0x9E, 0x01, 0xFC, 0x9B, + 0x31, 0xE8, 0x43, 0x3B, 0xAD, 0x7C, 0x02, 0x9F, 0x2F, 0x13, 0xCC, 0x10, 0x59, 0x2D, 0x23, 0x32, 0xE3, 0xE0, 0x8B, 0x80, 0xD3, 0x50, 0x46, 0x3D, 0xE7, 0x27, 0x50, 0xB1, 0xF8, 0x06, 0xF4, 0x93, + 0xE1, 0x43, 0xBD, 0x5F, 0xCA, 0x7D, 0x16, 0x98, 0x08, 0x1B, 0x31, 0xBF, 0x87, 0x6B, 0x2A, 0x1B, 0xC9, 0xDF, 0x50, 0x95, 0x2D, 0x13, 0xB6, 0xC1, 0x32, 0x1B, 0x11, 0x11, 0x17, 0x21, 0x45, 0xA6, + 0x27, 0xAE, 0x0B, 0x44, 0x27, 0xB9, 0x89, 0x75, 0xCB, 0xFF, 0xF7, 0xD6, 0x82, 0x75, 0x75, 0x4B, 0x45, 0xB6, 0x82, 0xD7, 0x09, 0xE1, 0x68, 0x52, 0x2E, 0x84, 0xFE, 0xA7, 0xDD, 0x3B, 0xB0, 0xF4, + 0x15, 0x05, 0xFF, 0x71, 0x92, 0x64, 0x31, 0xD1, 0xA9, 0x0D, 0x4C, 0xBF, 0x9A, 0x52, 0x7A, 0xD4, 0xE2, 0x84, 0x97, 0x6F, 0xFF, 0x8B, 0xD9, 0xD6, 0x22, 0x4A, 0x4F, 0x26, 0x03, 0x91, 0xA9, 0x87, + 0xFB, 0x6D, 0xA6, 0xEE, 0x42, 0xC2, 0xA4, 0x90, 0x0F, 0x40, 0x7C, 0xE1, 0xF0, 0x2E, 0x32, 0x24, 0x75, 0xD3, 0x13, 0xFB, 0xEB, 0xB6, 0x8C, 0x2E, 0x05, 0x73, 0x08, 0x09, 0x44, 0x8A, 0x74, 0x28, + 0xA5, 0x94, 0x01, 0x39, 0xEB, 0xDF, 0x1B, 0x55, 0x56, 0xFC, 0xC5, 0xD4, 0x2E, 0x1A, 0x13, 0xF3, 0x22, 0x30, 0xCB, 0x6F, 0x07, 0x24, 0x83, 0x1D, 0x0D, 0x07, 0x1B, 0xBA, 0x5A, 0x67, 0x04, 0x80, + 0x6F, 0x47, 0x5B, 0x74, 0xBA, 0x91, 0xB6, 0xE3, 0x85, 0xD4, 0x86, 0x20, 0x95, 0x8D, 0x0A, 0xB1, 0xBF, 0x2B, 0x18, 0x4E, 0x10, 0xF3, 0xE7, 0x53, 0xB7, 0x13, 0x37, 0xBE, 0x9E, 0xB6, 0x53, 0x78, + 0x67, 0x85, 0xB4, 0x3A, 0xC7, 0xE5, 0xC4, 0x94, 0xAC, 0x1B, 0xCB, 0x04, 0x3D, 0x46, 0x14, 0x25, 0xB3, 0x60, 0x98, 0xAC, 0x93, 0x05, 0x5A, 0x01, 0x05, 0xAB, 0x85, 0x23, 0xB6, 0x1D, 0x02, 0x4A, + 0x6E, 0x9B, 0x56, 0xA4, 0x2D, 0x3C, 0x04, 0x72, 0x65, 0x12, 0xAE, 0x4C, 0xFE, 0x05, 0x71, 0x04, 0x46, 0xB0, 0x6F, 0x69, 0x42, 0x34, 0xEE, 0x4F, 0xA8, 0xFE, 0xED, 0xDD, 0xC5, 0xF2, 0x8A, 0x65, + 0xED, 0xE2, 0xEB, 0x58, 0xE9, 0x65, 0xFE, 0x36, 0x27, 0xA5, 0x71, 0xBC, 0x45, 0xB3, 0x97, 0xED, 0x09, 0x2A, 0xB4, 0xBE, 0x00, 0x04, 0x17, 0x29, 0xC4, 0xD1, 0x92, 0xFE, 0x30, 0x67, 0x82, 0x79, + 0xD2, 0x23, 0xA8, 0x48, 0xCF, 0x43, 0x66, 0xE9, 0x2B, 0x3F, 0x68, 0xDE, 0xE9, 0x7C, 0x9B, 0x4A, 0x7F, 0xF2, 0x2F, 0x93, 0x7B, 0xE6, 0xC5, 0x66, 0x39, 0x96, 0x1D, 0xB2, 0x9F, 0xA3, 0xCF, 0xEC, + 0xFF, 0xF2, 0x93, 0x14, 0x08, 0x86, 0xFF, 0xB9, 0x2E, 0xBC, 0x79, 0xDA, 0xB5, 0x9C, 0xEA, 0xF8, 0x69, 0xC6, 0x4F, 0x8E, 0xAF, 0x58, 0x5C, 0xE9, 0x7D, 0xD6, 0xB7, 0x8F, 0x89, 0x27, 0x72, 0xDB, + 0x88, 0xA9, 0x58, 0xCF, 0x0A, 0xB5, 0x57, 0xA7, 0xFA, 0xA8, 0x3F, 0xE6, 0x21, 0x47, 0x7E, 0x2B, 0x84, 0x49, 0x7A, 0xB5, 0xA8, 0xEC, 0xF4, 0xA7, 0xBD, 0x32, 0xDF, 0xB9, 0x02, 0xF0, 0x5D, 0x2C, + 0xA3, 0x10, 0x47, 0xD0, 0xF1, 0x91, 0x9A, 0xDD, 0xE1, 0xEE, 0x6D, 0xFD, 0x58, 0xE5, 0x9B, 0xC4, 0xDA, 0xB3, 0xCC, 0xBB, 0xA3, 0x6A, 0xAA, 0xF6, 0xAF, 0xCC, 0xC7, 0xB0, 0x95, 0xCA, 0x94, 0xA1, + 0x95, 0xBE, 0x9A, 0x28, 0x95, 0x26, 0xB5, 0x88, 0xC3, 0xA9, 0xC5, 0x68, 0x76, 0xFC, 0x41, 0x5D, 0x52, 0x1D, 0x44, 0x2B, 0xAC, 0x02, 0x98, 0xD3, 0x02, 0x41, 0x9A, 0xD5, 0x27, 0xDA, 0x24, 0x9C, + 0x2A, 0x66, 0x0C, 0xD0, 0x64, 0x21, 0x3F, 0xFA, 0xD5, 0x63, 0x18, 0x3F, 0x37, 0x97, 0x25, 0x78, 0xEE, 0xB9, 0xF7, 0x0A, 0xC6, 0x7A, 0xEE, 0x6C, 0xC2, 0xB7, 0x1F, 0x28, 0x3A, 0x95, 0x93, 0x0B, + 0x55, 0x47, 0x38, 0x55, 0x57, 0x91, 0xC2, 0x5E, 0x7A, 0x39, 0x9E, 0x68, 0x56, 0x36, 0xD5, 0x8D, 0x69, 0xCB, 0x6B, 0xE7, 0x93, 0xB4, 0x5C, 0x19, 0x69, 0xE7, 0xD5, 0x61, 0x56, 0x27, 0xEB, 0xC3, + 0x2E, 0xED, 0x45, 0x44, 0x0F, 0x87, 0x88, 0x0D, 0x28, 0x29, 0xFA, 0x4F, 0xC8, 0x71, 0x86, 0x61, 0x64, 0xD2, 0x59, 0xED, 0x95, 0xD2, 0x73, 0x18, 0x71, 0x01, 0x7F, 0xF5, 0x18, 0x94, 0x06, 0x6F, + 0xAE, 0x1F, 0xFA, 0x6F, 0x4B, 0x4A, 0x6F, 0x84, 0xFC, 0xFF, 0xDA, 0x09, 0xE7, 0x18, 0xFA, 0x17, 0x13, 0x5E, 0xDB, 0x3F, 0x48, 0x55, 0x8D, 0x5B, 0xA6, 0x7F, 0x9E, 0x6F, 0x09, 0x00, 0x34, 0x0B, + 0xD0, 0x4D, 0xFE, 0x59, 0xB7, 0xBD, 0x67, 0x74, 0x58, 0x84, 0xFB, 0x84, 0xAE, 0x3F, 0x8E, 0xE7, 0x63, 0xD2, 0x02, 0x74, 0x36, 0x52, 0xD4, 0xF7, 0x33, 0x34, 0x50, 0x58, 0x04, 0x90, 0xB9, 0xC7, + 0x44, 0x93, 0x5B, 0x19, 0xC1, 0xD5, 0xFB, 0x0D, 0xB5, 0xFB, 0xB4, 0x61, 0x41, 0x13, 0x62, 0x83, 0x80, 0x37, 0xEB, 0x7E, 0xC3, 0xF6, 0x3F, 0x26, 0xC8, 0x93, 0xE7, 0xCC, 0x1C, 0x3B, 0x3F, 0x47, + 0x67, 0xAB, 0xAE, 0x00, 0xFE, 0xB7, 0xBB, 0x99, 0xB1, 0x42, 0x0B, 0xB2, 0x9E, 0xA6, 0x14, 0x74, 0x78, 0x96, 0xD9, 0xED, 0xCF, 0x81, 0x07, 0xFE, 0x50, 0x4C, 0x9C, 0x30, 0x8A, 0x82, 0x64, 0xDA, + 0xCE, 0x31, 0x8D, 0x87, 0xCF, 0xE4, 0x76, 0x18, 0x03, 0xE9, 0xA6, 0x0D, 0xEF, 0xA6, 0x14, 0x4A, 0xAB, 0xC1, 0xF1, 0x0A, 0x45, 0xB1, 0x40, 0xDE, 0xD7, 0x54, 0xE7, 0x35, 0x86, 0xC4, 0x67, 0xBB, + 0x7B, 0xF1, 0x9E, 0xDE, 0xF2, 0x5B, 0xE0, 0xC6, 0x5E, 0x93, 0xC5, 0xE5, 0xEB, 0x8F, 0x88, 0x0C, 0xCE, 0x4A, 0x85, 0x87, 0x57, 0xF8, 0xFF, 0x56, 0x06, 0x2B, 0x10, 0x67, 0xF4, 0x10, 0x6F, 0x76, + 0xB7, 0x00, 0x7F, 0x6E, 0xA6, 0xF9, 0x45, 0x04, 0x7E, 0x85, 0xBD, 0x0F, 0xAD, 0x9D, 0x26, 0x99, 0x4F, 0x67, 0x8A, 0x06, 0x12, 0xB8, 0x7C, 0xCF, 0x9C, 0x0C, 0xF9, 0xA4, 0x33, 0xD8, 0x89, 0xC9, + 0x6E, 0x4C, 0x12, 0xBE, 0x37, 0x22, 0x77, 0x00, 0x5B, 0x06, 0xAD, 0x12, 0x71, 0x05, 0xD1, 0x6D, 0x8F, 0xB1, 0x42, 0xAE, 0xAE, 0x53, 0x73, 0xAB, 0xD6, 0x1D, 0x9A, 0xDC, 0xFC, 0x55, 0x50, 0xD6, + 0x23, 0xCA, 0x3B, 0x88, 0x24, 0xB0, 0xE2, 0xE0, 0x8C, 0x2B, 0xF4, 0xE2, 0x84, 0x1E, 0xAC, 0x4C, 0x5D, 0xC5, 0x6C, 0xF8, 0x95, 0x4C, 0xF2, 0x07, 0xC2, 0x63, 0xF2, 0x7C, 0x9F, 0x30, 0x9F, 0x10, + 0x30, 0x7C, 0x0D, 0x84, 0xA6, 0x58, 0x78, 0x42, 0x50, 0x31, 0x37, 0x5D, 0xD8, 0x10, 0xD2, 0xD7, 0xE5, 0x10, 0x98, 0xA3, 0x81, 0x43, 0x50, 0x79, 0x5C, 0x4A, 0x07, 0x7F, 0xA4, 0x0D, 0xD4, 0x4F, + 0x0F, 0xA7, 0x51, 0x0F, 0x7C, 0x3F, 0x63, 0x14, 0x07, 0xCF, 0x34, 0xF6, 0x04, 0xC7, 0xB3, 0x35, 0x63, 0x2A, 0x20, 0xD2, 0xAD, 0x41, 0x9B, 0xD7, 0xCC, 0x6D, 0x42, 0x42, 0xB1, 0xC6, 0x6C, 0x35, + 0xE5, 0xA5, 0xED, 0xCC, 0xB1, 0x3C, 0xA3, 0x7D, 0x3B, 0x50, 0x46, 0x5F, 0x3B, 0x4A, 0xAF, 0xF7, 0xE3, 0x16, 0x1E, 0x79, 0x36, 0x08, 0x8A, 0xE0, 0x84, 0x01, 0xFD, 0x2C, 0x37, 0xD6, 0x7A, 0x2F, + 0xF9, 0x1D, 0x3E, 0x6F, 0x08, 0x68, 0x6D, 0x64, 0xBC, 0x2F, 0xC6, 0xC5, 0x71, 0x06, 0xE4, 0x9F, 0xA3, 0x84, 0xAC, 0x22, 0x21, 0x9F, 0x07, 0xEE, 0x89, 0x96, 0xCA, 0x3D, 0xFF, 0x59, 0xDC, 0xC5, + 0x09, 0x2A, 0x4B, 0xAD, 0xBE, 0x87, 0xAE, 0xDE, 0x7F, 0x69, 0xA0, 0x4C, 0x79, 0xB3, 0x3B, 0xDF, 0x35, 0xD4, 0xA0, 0xE4, 0xCB, 0x4B, 0x55, 0x01, 0x9C, 0xB0, 0xBF, 0x27, 0x52, 0x95, 0xB9, 0x3B, + 0xDA, 0xBE, 0xA5, 0x16, 0xCA, 0x2B, 0x61, 0x6A, 0x56, 0x91, 0x86, 0x00, 0xB7, 0x24, 0xBE, 0x7A, 0x01, 0xEC, 0x4E, 0xF5, 0x43, 0x12, 0xB3, 0x0D, 0x66, 0xF5, 0x07, 0x81, 0x5F, 0x27, 0x80, 0xFF, + 0xEE, 0x7C, 0x30, 0xF8, 0x42, 0x5A, 0x92, 0x25, 0x2C, 0xE5, 0x50, 0xFA, 0xB4, 0xE9, 0x02, 0xE7, 0xB3, 0x82, 0xD4, 0x6D, 0xBD, 0x20, 0xEF, 0xE1, 0xBB, 0x0E, 0xF8, 0xA4, 0x96, 0x87, 0x3C, 0x09, + 0xC4, 0xCE, 0xB0, 0x30, 0x3C, 0x7F, 0x1D, 0xAB, 0xA0, 0x10, 0x2D, 0xE9, 0x41, 0x90, 0xB6, 0xAC, 0x6D, 0xC8, 0x10, 0xF7, 0x2B, 0xCA, 0x3A, 0xA2, 0x92, 0xFF, 0x38, 0xBD, 0x51, 0xA7, 0xFA, 0xB8, + 0x50, 0x9E, 0xC4, 0xFB, 0xE0, 0xEA, 0xA3, 0xC9, 0x86, 0x16, 0x6A, 0x67, 0x4B, 0x78, 0x71, 0x15, 0x5C, 0x34, 0x8C, 0x47, 0x7E, 0xF8, 0xCE, 0xDC, 0x83, 0x2B, 0x5A, 0xBE, 0xE7, 0x1A, 0x8D, 0x18, + 0xD0, 0x6D, 0xD0, 0xF5, 0x22, 0x11, 0x60, 0xAB, 0xEB, 0x71, 0xE6, 0xE8, 0x2C, 0xFA, 0xBF, 0x73, 0x1E, 0xA3, 0x51, 0x5A, 0x76, 0xEF, 0x07, 0xB2, 0xC1, 0x6C, 0x63, 0xB3, 0x7F, 0x7A, 0xB7, 0x3B, + 0x67, 0xF0, 0x05, 0x92, 0x9A, 0x75, 0x3E, 0x45, 0x3B, 0x93, 0x0C, 0x0A, 0xF4, 0x32, 0x27, 0x7F, 0xD7, 0x7D, 0x8A, 0x1E, 0xB8, 0x02, 0x2C, 0xDE, 0x96, 0x65, 0x76, 0x3B, 0x01, 0x4F, 0x0A, 0x67, + 0x2A, 0x04, 0x16, 0x0B, 0x0A, 0x06, 0xF5, 0x54, 0x0F, 0x4C, 0x26, 0x4B, 0x7F, 0x22, 0x74, 0x06, 0x90, 0xA2, 0x35, 0x2D, 0xC8, 0x63, 0xB5, 0x88, 0x30, 0x3A, 0xD5, 0x1F, 0x0A, 0xE1, 0x62, 0xBF, + 0x79, 0x79, 0x7F, 0x07, 0xB5, 0x34, 0x50, 0x1C, 0xBB, 0xFD, 0xB7, 0x13, 0xA7, 0x24, 0xAA, 0x98, 0xE1, 0x95, 0x32, 0x18, 0x71, 0x80, 0xCC, 0xFA, 0xDC, 0x6E, 0xBE, 0x31, 0x42, 0xFA, 0x7D, 0xB6, + 0x6C, 0xD4, 0xDE, 0x7B, 0x9F, 0xBD, 0x4C, 0x82, 0x35, 0x68, 0x6D, 0xB6, 0x8C, 0xAF, 0x48, 0x9A, 0xFA, 0x4E, 0x1E, 0x87, 0xAE, 0xF0, 0xCE, 0xFD, 0x80, 0x37, 0xE3, 0xA5, 0x78, 0xEE, 0x62, 0xEB, + 0x7F, 0x94, 0xED, 0x5B, 0xC0, 0xB5, 0x8E, 0xEA, 0x4B, 0x4C, 0x45, 0xFC, 0x56, 0xD3, 0x1D, 0x29, 0x94, 0x4D, 0x09, 0x5A, 0xC9, 0x6C, 0x29, 0x08, 0x3D, 0xA2, 0xC7, 0x71, 0x81, 0xD9, 0x7A, 0x55, + 0xFE, 0x6E, 0x90, 0x3A, 0x2F, 0x27, 0x83, 0xDE, 0x0B, 0xAA, 0x5F, 0x47, 0xD7, 0x04, 0x78, 0x5C, 0x33, 0xE8, 0xD5, 0xC8, 0x7E, 0xD6, 0x1E, 0x65, 0x45, 0x91, 0x67, 0x31, 0x0E, 0xB7, 0xA9, 0x95, + 0x74, 0xEF, 0x81, 0x9A, 0xE9, 0x16, 0x1A, 0x3B, 0xD0, 0x96, 0x34, 0x80, 0x3D, 0x9E, 0x1E, 0x4E, 0xC7, 0x38, 0x6D, 0x79, 0x46, 0x98, 0x45, 0x17, 0x21, 0x3A, 0xB9, 0xCF, 0x66, 0xAE, 0xA5, 0x51, + 0xCC, 0x45, 0x7C, 0x39, 0xF8, 0x6A, 0xF2, 0x94, 0xCF, 0x7B, 0x07, 0x3F, 0x56, 0x3E, 0xD4, 0xDA, 0xB9, 0x41, 0x9B, 0xDF, 0x00, 0x4B, 0xD0, 0x5C, 0x92, 0xB4, 0xE8, 0x0E, 0xC3, 0xCF, 0xEA, 0xC9, + 0x7E, 0x1D, 0xDA, 0x55, 0x4F, 0xDA, 0x62, 0x5C, 0x4B, 0x9B, 0x03, 0x9B, 0xAA, 0x7C, 0x5A, 0x2F, 0x6F, 0x97, 0x05, 0x77, 0x92, 0x48, 0x3C, 0xF5, 0xF8, 0x52, 0xD4, 0xC3, 0xAC, 0x71, 0xAD, 0x50, + 0xF7, 0x79, 0x95, 0x3D, 0xCF, 0xE2, 0xF6, 0x3E, 0xD2, 0x35, 0xD8, 0xE1, 0xD5, 0x34, 0x5D, 0x6C, 0x6D, 0xF0, 0x55, 0x5C, 0xC2, 0x63, 0x1D, 0xEA, 0xD9, 0xB7, 0x14, 0xBC, 0x4C, 0x16, 0x50, 0x1E, + 0x01, 0x26, 0x13, 0x81, 0xF3, 0x67, 0x97, 0x15, 0x34, 0x51, 0x23, 0x38, 0x8C, 0x85, 0x2D, 0x57, 0xDC, 0xF1, 0x94, 0x1D, 0x09, 0x11, 0xD4, 0x9F, 0xEA, 0x71, 0x43, 0xFD, 0x2F, 0xC3, 0x43, 0xA5, + 0x07, 0x5B, 0x64, 0xCC, 0xA4, 0x82, 0x91, 0xDC, 0x28, 0xB8, 0x3F, 0x76, 0x07, 0x45, 0x89, 0xEA, 0xB2, 0x17, 0xC7, 0x84, 0x78, 0x40, 0x65, 0x2C, 0x0E, 0x3A, 0xE2, 0x78, 0xB3, 0xB6, 0xFB, 0x0D, + 0x80, 0x0C, 0x5E, 0x7D, 0xB7, 0x9D, 0x5C, 0xB9, 0xCC, 0x1A, 0x87, 0x45, 0x0C, 0x00, 0xB7, 0x67, 0x78, 0x12, 0xD2, 0x2E, 0xE2, 0x0F, 0xDE, 0x8C, 0x17, 0x53, 0xA7, 0xFB, 0x93, 0xBA, 0x8B, 0xBB, + 0x85, 0x95, 0xA6, 0x39, 0x3D, 0xF5, 0x4A, 0xA9, 0xCD, 0xB6, 0xE0, 0x87, 0x9A, 0x26, 0xE4, 0x9B, 0xD3, 0xB0, 0x15, 0x13, 0xC6, 0x05, 0x3A, 0x07, 0x46, 0xC8, 0x59, 0x6C, 0xE5, 0xE5, 0xB2, 0x25, + 0xCF, 0xCA, 0x26, 0xAB, 0x8B, 0xF1, 0x2F, 0x1F, 0xE0, 0xA6, 0x47, 0xA9, 0xE4, 0x45, 0x30, 0x39, 0xA1, 0x22, 0x61, 0x94, 0xC4, 0x6E, 0x8B, 0x98, 0xAC, 0xD7, 0x10, 0xF1, 0x8F, 0xB7, 0xEC, 0x05, + 0x47, 0x6C, 0x1C, 0xD8, 0xFC, 0x31, 0x12, 0xCC, 0xDD, 0xB1, 0x58, 0x2B, 0x88, 0x17, 0xC1, 0x8F, 0xE3, 0x15, 0x35, 0x3E, 0x7A, 0x47, 0xC8, 0x21, 0xE9, 0xEE, 0x3A, 0x43, 0xCA, 0xDE, 0x1B, 0x80, + 0xD9, 0x2A, 0x0A, 0xE8, 0xDC, 0xEB, 0x4D, 0xFF, 0x76, 0x6A, 0x54, 0xDF, 0x36, 0x65, 0xFE, 0xFE, 0x3C, 0x25, 0x2B, 0x72, 0xDA, 0xD7, 0xB1, 0xE3, 0x35, 0x9E, 0x7F, 0xA2, 0x55, 0x62, 0xC3, 0xE3, + 0x9D, 0xB5, 0x21, 0xCE, 0x18, 0x74, 0x11, 0x1F, 0xB0, 0x90, 0xDB, 0xD3, 0x8B, 0x31, 0x80, 0xAD, 0x03, 0x4B, 0x57, 0xB0, 0x31, 0xDC, 0x4D, 0xD6, 0xAF, 0x7C, 0x1A, 0x8A, 0xF3, 0xF6, 0xCE, 0x7E, + 0xDB, 0x1A, 0x9E, 0x4B, 0x6D, 0x4A, 0x59, 0x20, 0xE3, 0x62, 0x08, 0x18, 0x82, 0x06, 0x59, 0x76, 0x2E, 0xF7, 0xA4, 0x24, 0x3F, 0x51, 0xDF, 0x2D, 0x8A, 0x90, 0x07, 0x37, 0xD5, 0x81, 0x05, 0x69, + 0x9B, 0x4E, 0x10, 0xCB, 0xCB, 0x35, 0x9C, 0x7F, 0x3A, 0x40, 0x07, 0x69, 0x7C, 0x48, 0x20, 0x50, 0xEC, 0x33, 0xCF, 0x80, 0x41, 0x91, 0x6A, 0x3B, 0x91, 0x9A, 0x50, 0xD9, 0x6E, 0xF0, 0xF5, 0x89, + 0xFD, 0x45, 0x56, 0xF3, 0x0D, 0xBD, 0xD9, 0x42, 0xEA, 0xB7, 0x9D, 0xFA, 0x97, 0xC0, 0x7E, 0x30, 0x24, 0x70, 0x74, 0x35, 0x2E, 0x1B, 0xF9, 0x8E, 0x34, 0x9C, 0xC7, 0xEF, 0xA5, 0xA1, 0xB8, 0xFC, + 0xE4, 0xF1, 0x8F, 0x1F, 0xAF, 0x6F, 0x07, 0xC9, 0x9C, 0x32, 0x14, 0x48, 0xB0, 0x39, 0x5C, 0x8A, 0x9C, 0xBC, 0x46, 0x64, 0x12, 0xF8, 0x9C, 0x1A, 0x98, 0xBF, 0x57, 0x15, 0x84, 0x28, 0x44, 0xF0, + 0xE8, 0x23, 0x6F, 0xA4, 0x69, 0x6C, 0x46, 0x58, 0xB8, 0xFD, 0xE4, 0x42, 0x5D, 0x09, 0xD6, 0x7A, 0x38, 0xAC, 0x72, 0x58, 0xE5, 0xD5, 0x96, 0x6F, 0x2D, 0x3F, 0xF6, 0x6A, 0x0C, 0x0C, 0xE7, 0x6E, + 0x7F, 0x6B, 0x81, 0xA1, 0xBC, 0xD0, 0x47, 0xFD, 0x3A, 0x20, 0x5B, 0xF0, 0xCC, 0xAE, 0xA3, 0xB1, 0x10, 0x79, 0x90, 0x9C, 0x6C, 0xE5, 0x69, 0x8F, 0x32, 0xE1, 0xF3, 0x40, 0x96, 0x58, 0xFF, 0xA0, + 0x1E, 0xAE, 0xCB, 0x4A, 0xE2, 0xB0, 0x92, 0xB7, 0x89, 0x89, 0xDA, 0xAD, 0x66, 0x23, 0xBB, 0x11, 0xF4, 0x9F, 0x0F, 0x8F, 0x86, 0x99, 0xEC, 0x05, 0x66, 0x15, 0x02, 0xFF, 0xCA, 0xD0, 0x3C, 0xF4, + 0x15, 0x19, 0x1A, 0x22, 0x2D, 0x3C, 0x4C, 0x7B, 0x8A, 0xB0, 0xB5, 0xB9, 0xBB, 0xC2, 0xD9, 0xDC, 0xEF, 0xF7, 0x20, 0x2D, 0x3F, 0x42, 0x44, 0x49, 0x4F, 0x52, 0x53, 0x64, 0x66, 0x69, 0x74, 0xC4, + 0xD9, 0xE6, 0xF5, 0xFA, 0x00, 0x01, 0x04, 0x19, 0x27, 0x37, 0x3D, 0x5A, 0x76, 0x80, 0xB8, 0xC1, 0xC9, 0xFE, 0x20, 0x29, 0x38, 0x3B, 0x3C, 0x48, 0x4D, 0x56, 0x5F, 0x65, 0x79, 0x9D, 0x9E, 0xA6, + 0xA9, 0xAD, 0xD2, 0xDE, 0xE5, 0xE7, 0xF7, 0xF9, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x12, 0x24, 0x32, 0x48, + }, + }, + { + .name = "Dilithium Round 3, Level 3 (4-4) KAT 1", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_44, + .rho_len = 32, + .rho = { + 0xB5, 0x41, 0xC1, 0xE9, 0x2C, 0xEA, 0xDD, 0x90, 0x4A, 0x09, 0xEC, 0x08, 0xAD, 0x30, 0x6D, 0x97, 0x47, 0x34, 0xA0, 0x77, 0x86, 0x84, 0x71, 0xE5, 0x8D, 0x07, 0x71, 0x87, 0xC4, 0x66, 0x04, 0xCF, + }, + .seed_len = 32, + .seed = { + 0x95, 0x2D, 0x21, 0x81, 0xAC, 0x1F, 0x62, 0x59, 0x6F, 0x76, 0x7E, 0xFC, 0xA0, 0xB5, 0x5D, 0xB0, 0x92, 0xEF, 0x81, 0xDB, 0x66, 0xF9, 0xFF, 0xF1, 0x5F, 0x13, 0xD7, 0xAE, 0xEA, 0xCD, 0x8B, 0x3A, + }, + .tr_len = 32, + .tr = { + 0x57, 0x96, 0xFB, 0xFE, 0x5B, 0x4E, 0x2E, 0xDE, 0xC5, 0xDB, 0xC9, 0x52, 0xF6, 0x0E, 0xB1, 0x22, 0x90, 0x18, 0x93, 0xCA, 0x25, 0x2D, 0xD7, 0x30, 0x41, 0x2A, 0xC4, 0xB6, 0xE0, 0x20, 0x09, 0x71, + }, + .s1_len = 384, + .s1 = { + 0x03, 0x40, 0x28, 0x8C, 0x88, 0x60, 0x21, 0xB1, 0x90, 0x0C, 0x12, 0x0D, 0x58, 0x18, 0x09, 0x23, 0x44, 0x86, 0x03, 0x02, 0x84, 0x89, 0xB2, 0x28, 0x0C, 0x97, 0x2C, 0x11, 0xC2, 0x09, 0x18, 0x32, + 0x08, 0x09, 0x10, 0x91, 0x14, 0x82, 0x8C, 0x13, 0x03, 0x05, 0x11, 0x01, 0x4C, 0x62, 0x18, 0x8A, 0xDB, 0x08, 0x8A, 0x93, 0x38, 0x12, 0x09, 0xA9, 0x20, 0xE4, 0xA8, 0x41, 0x1A, 0xA1, 0x40, 0xD1, + 0x42, 0x2E, 0x59, 0x92, 0x24, 0xD0, 0x26, 0x00, 0x19, 0x93, 0x84, 0xE2, 0x28, 0x92, 0x1B, 0x19, 0x50, 0xA3, 0x10, 0x8E, 0xA2, 0x28, 0x20, 0x93, 0x34, 0x70, 0x94, 0xC0, 0x4D, 0x24, 0x35, 0x41, + 0x14, 0x05, 0x62, 0xC2, 0x22, 0x31, 0x1A, 0x38, 0x4E, 0xCC, 0x42, 0x44, 0x13, 0x20, 0x82, 0x08, 0x18, 0x6D, 0xE0, 0x14, 0x0D, 0x01, 0x36, 0x61, 0x08, 0x22, 0x29, 0x14, 0xB5, 0x11, 0x49, 0x22, + 0x32, 0xE2, 0x42, 0x26, 0xE4, 0x04, 0x01, 0x5B, 0x48, 0x2A, 0x11, 0x02, 0x60, 0x63, 0x02, 0x48, 0x4A, 0x24, 0x2C, 0x62, 0x40, 0x90, 0x03, 0x41, 0x8D, 0x18, 0xC8, 0x30, 0x82, 0x02, 0x82, 0x51, + 0x98, 0x69, 0xA2, 0x24, 0x50, 0x0A, 0x39, 0x4D, 0x84, 0x00, 0x8E, 0x84, 0x08, 0x21, 0xD9, 0x30, 0x6C, 0xE3, 0x18, 0x29, 0x23, 0x45, 0x6E, 0xCA, 0x24, 0x66, 0x08, 0x21, 0x49, 0x14, 0x16, 0x52, + 0xDA, 0xA0, 0x0C, 0x22, 0x19, 0x62, 0xC1, 0xB8, 0x08, 0x8A, 0x88, 0x8C, 0x22, 0xB1, 0x0C, 0x23, 0xB8, 0x0D, 0x00, 0x93, 0x64, 0x93, 0x16, 0x82, 0x63, 0x32, 0x30, 0xDC, 0xA2, 0x41, 0xD1, 0x48, + 0x42, 0x82, 0xA2, 0x64, 0xD4, 0x24, 0x48, 0x94, 0x48, 0x25, 0x02, 0x82, 0x65, 0xD9, 0x08, 0x69, 0x12, 0x44, 0x21, 0x54, 0x24, 0x70, 0x04, 0x80, 0x84, 0xDA, 0x44, 0x25, 0xA0, 0x24, 0x8A, 0x13, + 0x35, 0x60, 0x84, 0xA0, 0x4C, 0x93, 0x90, 0x48, 0x13, 0x47, 0x02, 0x83, 0x20, 0x05, 0x64, 0xB4, 0x0C, 0x5C, 0x12, 0x72, 0x42, 0x14, 0x86, 0x60, 0x02, 0x12, 0x50, 0x44, 0x04, 0x0B, 0x82, 0x11, + 0x91, 0x18, 0x72, 0x48, 0x88, 0x10, 0xD0, 0x40, 0x4D, 0xCB, 0x98, 0x51, 0x49, 0xA4, 0x8D, 0x18, 0x25, 0x89, 0xD4, 0x32, 0x8E, 0x52, 0xA4, 0x10, 0x11, 0x40, 0x12, 0x88, 0x26, 0x88, 0x21, 0x17, + 0x6A, 0xA2, 0xB2, 0x41, 0xE4, 0x02, 0x89, 0xA1, 0xA0, 0x30, 0x94, 0xC8, 0x41, 0x1B, 0x83, 0x64, 0x12, 0x05, 0x0A, 0x1C, 0x43, 0x8C, 0x84, 0x06, 0x31, 0x0A, 0xA2, 0x6D, 0x24, 0x17, 0x31, 0xC3, + 0x98, 0x28, 0x42, 0x88, 0x25, 0x8C, 0x30, 0x52, 0xA0, 0x02, 0x0E, 0x98, 0x36, 0x88, 0x03, 0x81, 0x31, 0x64, 0x18, 0x6C, 0x09, 0x82, 0x69, 0x19, 0x41, 0x4C, 0xA0, 0x26, 0x11, 0x23, 0x35, 0x60, + }, + .s2_len = 384, + .s2 = { + 0x01, 0x04, 0x85, 0x64, 0x86, 0x30, 0xD9, 0x20, 0x84, 0xD9, 0x08, 0x2A, 0xDC, 0x32, 0x61, 0x1C, 0xC2, 0x80, 0x89, 0x82, 0x51, 0x14, 0x10, 0x40, 0x19, 0x05, 0x80, 0x58, 0x04, 0x06, 0x99, 0x08, + 0x84, 0x09, 0x27, 0x41, 0xCA, 0x20, 0x8A, 0x93, 0x00, 0x91, 0x03, 0xC6, 0x81, 0xC2, 0xC8, 0x09, 0xC3, 0x30, 0x4D, 0x23, 0x12, 0x0A, 0x9B, 0x42, 0x8D, 0x20, 0x23, 0x6A, 0x54, 0x30, 0x22, 0xCC, + 0xA4, 0x29, 0xA2, 0x18, 0x31, 0x40, 0x20, 0x6E, 0x92, 0x90, 0x48, 0x41, 0xB8, 0x45, 0x83, 0x38, 0x08, 0x5C, 0x46, 0x80, 0x59, 0x36, 0x45, 0xE3, 0xB0, 0x31, 0x18, 0x06, 0x6A, 0x53, 0x16, 0x6D, + 0x21, 0x99, 0x81, 0x00, 0x30, 0x4E, 0xC8, 0x26, 0x48, 0x18, 0xC0, 0x88, 0x19, 0x14, 0x92, 0xC1, 0x98, 0x45, 0x98, 0x08, 0x84, 0x9B, 0x10, 0x4D, 0x0C, 0x96, 0x90, 0x08, 0x91, 0x69, 0x0C, 0xB1, + 0x4D, 0x91, 0x28, 0x6E, 0xC9, 0x06, 0x8C, 0x58, 0x00, 0x0A, 0x0C, 0x96, 0x05, 0x8A, 0x46, 0x06, 0xD4, 0x98, 0x29, 0x83, 0x26, 0x50, 0xE1, 0x10, 0x61, 0xD0, 0x96, 0x50, 0x23, 0x12, 0x24, 0x52, + 0x20, 0x80, 0xE4, 0x04, 0x48, 0x0C, 0x23, 0x92, 0x0B, 0xB7, 0x0D, 0x0C, 0x82, 0x90, 0xD1, 0x10, 0x90, 0x21, 0x22, 0x11, 0x0A, 0x12, 0x64, 0x53, 0xB6, 0x71, 0x99, 0x28, 0x69, 0xC1, 0xC4, 0x4D, + 0x04, 0xA0, 0x8D, 0xCB, 0x96, 0x41, 0x58, 0x14, 0x06, 0x0C, 0x21, 0x70, 0x8B, 0x30, 0x25, 0x52, 0xA2, 0x25, 0x21, 0x19, 0x30, 0x00, 0xA3, 0x28, 0xD0, 0xB8, 0x09, 0xCC, 0x16, 0x12, 0xDC, 0x94, + 0x6D, 0x01, 0x20, 0x81, 0xDC, 0x42, 0x42, 0xE1, 0x28, 0x01, 0x0C, 0x87, 0x89, 0x02, 0x84, 0x09, 0x02, 0x17, 0x88, 0xD8, 0x34, 0x30, 0x1C, 0x33, 0x64, 0x44, 0xA0, 0x09, 0xA0, 0xA0, 0x0D, 0xE3, + 0x90, 0x4D, 0x01, 0x08, 0x65, 0xE2, 0x42, 0x69, 0xA2, 0xC0, 0x91, 0x99, 0x16, 0x62, 0x9B, 0x02, 0x60, 0x40, 0x88, 0x50, 0x40, 0x86, 0x71, 0xA4, 0xC4, 0x61, 0x62, 0x22, 0x20, 0x10, 0x12, 0x11, + 0x4B, 0x26, 0x22, 0x09, 0x07, 0x88, 0x1A, 0x26, 0x85, 0x58, 0x86, 0x80, 0xDA, 0xA0, 0x8C, 0x0B, 0x85, 0x68, 0x42, 0x22, 0x82, 0x88, 0x24, 0x61, 0x8C, 0x98, 0x8C, 0x23, 0x30, 0x25, 0x24, 0x40, + 0x45, 0x08, 0xC8, 0x6C, 0x23, 0x14, 0x28, 0x4A, 0x28, 0x10, 0x81, 0x20, 0x72, 0x88, 0x32, 0x26, 0x93, 0xA6, 0x6D, 0x5B, 0xB6, 0x29, 0xC1, 0x24, 0x0D, 0x49, 0x20, 0x70, 0x59, 0x48, 0x26, 0x20, + 0x26, 0x65, 0xCB, 0xA4, 0x88, 0x4A, 0xA6, 0x30, 0x08, 0x45, 0x8E, 0x00, 0x32, 0x88, 0x24, 0x33, 0x0D, 0xA1, 0x46, 0x72, 0x9B, 0x12, 0x00, 0x14, 0xB5, 0x21, 0xE3, 0x02, 0x09, 0x23, 0x42, 0x28, + }, + .t0_len = 1664, + .t0 = { + 0x2A, 0xD8, 0xD7, 0x4C, 0xE8, 0x1B, 0x82, 0x66, 0x32, 0x1C, 0x15, 0xEA, 0x97, 0x8C, 0xCC, 0x75, 0xCC, 0x04, 0x3E, 0x18, 0xFA, 0x5B, 0x8E, 0x92, 0x21, 0x9E, 0x47, 0x6F, 0x1F, 0x36, 0xA1, 0x92, + 0x43, 0x5C, 0x3F, 0x9B, 0x0A, 0xD4, 0xA6, 0x80, 0x32, 0x18, 0xAA, 0xA1, 0x48, 0x1E, 0x6D, 0x8A, 0x89, 0x48, 0xF1, 0xF6, 0xE0, 0x40, 0x54, 0xBC, 0x30, 0x7F, 0x5B, 0x19, 0xC4, 0x2E, 0x66, 0x90, + 0x2C, 0x8C, 0x44, 0xF2, 0xDC, 0xA9, 0xAC, 0x1B, 0xC0, 0x1E, 0x57, 0x6D, 0x59, 0xCA, 0xDC, 0x5C, 0x69, 0x09, 0x02, 0x35, 0xB0, 0x3D, 0x49, 0xA1, 0x09, 0xD9, 0x97, 0xD6, 0x25, 0x68, 0x26, 0xAE, + 0xCC, 0x7E, 0xD0, 0xC1, 0x7D, 0xB4, 0xEB, 0x50, 0xCB, 0x82, 0xE6, 0xF1, 0x79, 0xFC, 0x67, 0xAF, 0x16, 0x8F, 0xF5, 0x3E, 0xDA, 0x67, 0x44, 0xBB, 0xF0, 0x92, 0xCE, 0x8A, 0x1F, 0x01, 0xFE, 0xEA, + 0x71, 0xB4, 0xD1, 0xA9, 0xB2, 0x7D, 0x6E, 0x21, 0x68, 0x98, 0x38, 0xAB, 0x07, 0x69, 0xFF, 0xD7, 0x59, 0x3A, 0x2B, 0x06, 0x29, 0x72, 0xB3, 0x80, 0xD9, 0xB2, 0x9C, 0x98, 0x7D, 0xC7, 0x60, 0x39, + 0x10, 0xC1, 0x5F, 0x4B, 0xD1, 0x98, 0xCE, 0xB6, 0x57, 0xBD, 0x10, 0x3C, 0x2A, 0x43, 0xC7, 0x6D, 0x89, 0xB9, 0x77, 0x90, 0x1F, 0x4E, 0x0E, 0x9C, 0xD8, 0xAC, 0x60, 0x22, 0x8F, 0x96, 0x27, 0x86, + 0x49, 0x0A, 0x65, 0xFF, 0xE9, 0x10, 0x4B, 0x9A, 0x6C, 0x32, 0xCF, 0xDE, 0xA6, 0xD0, 0x77, 0x79, 0x17, 0x56, 0x5F, 0xF3, 0x25, 0xD1, 0x19, 0x37, 0x32, 0x32, 0xF9, 0x14, 0xCD, 0xD1, 0xBB, 0xBA, + 0xF9, 0x34, 0x45, 0x4D, 0x79, 0x5C, 0xE6, 0xDB, 0xE4, 0xD1, 0x5D, 0x67, 0x27, 0x31, 0xA7, 0x1A, 0x5B, 0xB8, 0x30, 0x43, 0xEB, 0x76, 0x8F, 0x8A, 0x91, 0x85, 0x0A, 0xF4, 0x7C, 0xF5, 0x33, 0xBF, + 0x95, 0xEA, 0x40, 0xDB, 0xDD, 0x4F, 0x37, 0xAC, 0x84, 0x93, 0x43, 0x86, 0x06, 0x1E, 0xD5, 0xB5, 0x41, 0xC5, 0x61, 0x6C, 0x68, 0xCA, 0x55, 0xE2, 0xE7, 0xB8, 0x7A, 0x16, 0x28, 0xFA, 0x55, 0x52, + 0xA0, 0x48, 0xC0, 0x93, 0x29, 0x6E, 0x22, 0xCE, 0x02, 0x88, 0xC7, 0x6E, 0x7A, 0x13, 0x03, 0xD4, 0xE7, 0x01, 0x23, 0xDD, 0xCF, 0xCF, 0x43, 0xA0, 0x15, 0xDE, 0xE8, 0x39, 0x95, 0x9E, 0x04, 0x4F, + 0x7C, 0xBF, 0x57, 0x84, 0xE4, 0x9F, 0x1E, 0xA3, 0x54, 0x00, 0x08, 0x60, 0xB9, 0x56, 0x1B, 0xC4, 0xED, 0xBD, 0xF9, 0x68, 0x20, 0x97, 0xEA, 0xFB, 0xEB, 0xE5, 0x21, 0x5C, 0x8B, 0x4E, 0x8B, 0x03, + 0xD1, 0x3A, 0x29, 0x76, 0x5E, 0xE3, 0xF0, 0x53, 0x3F, 0x79, 0x34, 0x28, 0xE2, 0x62, 0xF3, 0x38, 0x54, 0xA6, 0xFE, 0x00, 0x3C, 0x28, 0x4B, 0xDC, 0xB6, 0x6C, 0xD6, 0x8F, 0x98, 0xFB, 0xAA, 0x02, + 0x02, 0xCD, 0x1B, 0x85, 0x42, 0x32, 0x5A, 0x15, 0xAA, 0xA2, 0xD2, 0xE7, 0xF8, 0x38, 0xB6, 0x2D, 0x7C, 0x03, 0x64, 0x01, 0x6A, 0xFD, 0xC0, 0x6F, 0xA3, 0xFA, 0x85, 0xAE, 0x8F, 0x8B, 0x1B, 0xEA, + 0x4E, 0x62, 0xAA, 0xDF, 0x96, 0x61, 0x82, 0x56, 0x18, 0x5E, 0x6E, 0xF3, 0x1B, 0xF3, 0x0C, 0xAD, 0x1F, 0x72, 0x7F, 0x67, 0x98, 0x0D, 0x03, 0xF7, 0x52, 0xE1, 0x93, 0x64, 0xE5, 0x92, 0xA6, 0xF8, + 0xF9, 0x84, 0x95, 0x3E, 0x29, 0x31, 0xA1, 0xA2, 0xF6, 0xEA, 0x01, 0x11, 0xE5, 0x5B, 0xDA, 0x28, 0xA9, 0xFA, 0x6C, 0x05, 0xBB, 0x00, 0x0F, 0x6A, 0x32, 0x03, 0x93, 0x97, 0xA2, 0xA1, 0x97, 0x67, + 0x17, 0x26, 0x4B, 0x54, 0xF4, 0x76, 0xE7, 0x09, 0xF6, 0x5B, 0xBA, 0x59, 0x20, 0x33, 0x49, 0x93, 0x0B, 0x18, 0x69, 0x8F, 0x6F, 0xA8, 0x64, 0xE1, 0x47, 0x6B, 0xAD, 0xB4, 0x2E, 0x41, 0xC6, 0xD9, + 0xF6, 0xA7, 0xA6, 0x8B, 0x31, 0x6E, 0xA0, 0xC6, 0x2D, 0x3F, 0x01, 0x31, 0x93, 0x4E, 0xD8, 0xD2, 0x90, 0x22, 0xE6, 0x7D, 0x87, 0x12, 0x2C, 0x62, 0x48, 0x68, 0x86, 0x10, 0x7E, 0x8D, 0x45, 0x9D, + 0x68, 0x65, 0xE8, 0xA4, 0x3B, 0x3F, 0xCF, 0xFA, 0x27, 0xAE, 0xF2, 0x2C, 0x04, 0x8A, 0x31, 0x35, 0xEE, 0x8A, 0x85, 0x7E, 0x81, 0x3C, 0x24, 0x72, 0x5B, 0x43, 0xF4, 0x26, 0x57, 0xBE, 0xDE, 0xDD, + 0x37, 0x3E, 0xD8, 0x5E, 0x39, 0x07, 0x0C, 0x58, 0x5F, 0x1D, 0x78, 0xD7, 0xAD, 0xE4, 0xC4, 0x4A, 0x20, 0x82, 0x27, 0x0A, 0xA6, 0x32, 0x29, 0xA1, 0x64, 0xFC, 0x04, 0x6A, 0x34, 0x41, 0x90, 0x83, + 0x57, 0x4E, 0x66, 0xC2, 0xB4, 0x4B, 0x13, 0xDF, 0x71, 0x70, 0x4A, 0xE3, 0x89, 0x05, 0x18, 0x66, 0x61, 0x5B, 0xF1, 0xB2, 0x11, 0x97, 0x0E, 0x40, 0x33, 0x06, 0xBD, 0xF1, 0x51, 0x02, 0xB8, 0x31, + 0x44, 0x8B, 0x23, 0xAE, 0xB1, 0x9F, 0x48, 0x69, 0xE9, 0x37, 0x33, 0x3F, 0x67, 0x88, 0xE4, 0xC2, 0x94, 0x31, 0x27, 0xC6, 0x4E, 0x21, 0xCF, 0xC2, 0x99, 0xAD, 0xD8, 0x48, 0xFD, 0x4E, 0xE4, 0x0B, + 0x89, 0x1A, 0x8A, 0x5F, 0x51, 0xD1, 0x7A, 0x51, 0x0F, 0x57, 0xA5, 0x4C, 0xD3, 0xD8, 0x3E, 0x86, 0xD0, 0x7B, 0x50, 0x4E, 0xDF, 0x33, 0xE0, 0xDE, 0xED, 0xAC, 0xF7, 0x66, 0xE9, 0x6F, 0x87, 0x05, + 0x39, 0x3F, 0xDA, 0xCF, 0xB8, 0x31, 0xBD, 0x42, 0x52, 0xA1, 0x52, 0xF1, 0x49, 0x8D, 0xE3, 0x59, 0xA8, 0xA6, 0x3B, 0x71, 0x61, 0x4E, 0x9A, 0xB3, 0x73, 0x52, 0x61, 0xC8, 0xA6, 0xA9, 0xB3, 0x5E, + 0x13, 0x6A, 0x66, 0x04, 0x97, 0x52, 0x02, 0x95, 0x0E, 0x97, 0xFF, 0x52, 0xC7, 0x58, 0xC1, 0x9E, 0x5A, 0x3B, 0x7A, 0xAB, 0x9C, 0xCA, 0xC7, 0x95, 0xDA, 0xE7, 0x19, 0x9D, 0xC0, 0x39, 0xD6, 0x56, + 0x67, 0xDB, 0xC6, 0xFD, 0x54, 0xA4, 0xF7, 0x84, 0xFB, 0xD7, 0x24, 0xF1, 0x0D, 0x17, 0x93, 0x4B, 0x81, 0x29, 0xA7, 0xFB, 0xF9, 0xA2, 0x57, 0x73, 0x53, 0xF4, 0x9F, 0xE5, 0x34, 0x7C, 0x66, 0x99, + 0x05, 0x23, 0xAD, 0x4F, 0x42, 0x95, 0x35, 0x2F, 0xAE, 0x6C, 0x08, 0x55, 0xE5, 0x40, 0xBB, 0x0E, 0xA6, 0x16, 0xE3, 0x04, 0xEB, 0x26, 0x0C, 0x80, 0xB8, 0x79, 0x20, 0xB9, 0x24, 0xF5, 0xAB, 0x8C, + 0x9C, 0x74, 0x5D, 0x45, 0xEE, 0x0E, 0xC0, 0xD1, 0x9B, 0xBB, 0x9E, 0x4D, 0x94, 0xEA, 0x4D, 0xCF, 0x31, 0xC1, 0x67, 0xA4, 0x8D, 0x14, 0xA7, 0x0D, 0xB0, 0x24, 0x9B, 0xCB, 0xAE, 0x69, 0xA0, 0x79, + 0xC9, 0x50, 0xAB, 0x2C, 0xF0, 0x53, 0x59, 0x5F, 0xBC, 0xB6, 0x1C, 0x1A, 0xFE, 0x13, 0xE7, 0x4C, 0xE1, 0xA9, 0x73, 0xCA, 0x55, 0xC7, 0x49, 0x77, 0x21, 0xE3, 0xFA, 0xD9, 0xF5, 0x57, 0xD6, 0x71, + 0xB3, 0x0B, 0x6C, 0x49, 0xA6, 0x38, 0xA1, 0xEB, 0x2C, 0x4A, 0xC9, 0xBD, 0x6C, 0x68, 0xBF, 0xB5, 0x33, 0xD4, 0xDE, 0xDE, 0xAD, 0xC8, 0xEA, 0xB6, 0x48, 0xA1, 0x1A, 0x97, 0xAF, 0x9C, 0x76, 0x15, + 0xE4, 0x15, 0x7C, 0xD0, 0x74, 0x97, 0xE8, 0xBA, 0x6E, 0xBB, 0x8A, 0xA3, 0x4C, 0x89, 0xFF, 0x42, 0xF7, 0x66, 0x04, 0x38, 0x00, 0xBA, 0xC8, 0xD0, 0x7C, 0x94, 0x7B, 0xD0, 0x0D, 0xAF, 0xA4, 0x25, + 0x39, 0xBD, 0x78, 0x81, 0x31, 0x71, 0x7D, 0x1D, 0x1D, 0xE3, 0x54, 0xFD, 0xDF, 0x30, 0xDC, 0xCC, 0xFD, 0x62, 0x2F, 0x6C, 0xDD, 0xF0, 0x34, 0xC8, 0x9D, 0x19, 0xC0, 0x15, 0xF3, 0x7E, 0xC3, 0x26, + 0x25, 0x7F, 0xB6, 0x1C, 0xA6, 0x67, 0x73, 0x6D, 0x9C, 0x72, 0x39, 0xA8, 0x1F, 0x84, 0xEF, 0x76, 0x16, 0xA1, 0x45, 0x85, 0x6B, 0xB9, 0x79, 0x29, 0x04, 0xE8, 0xD5, 0x0E, 0x93, 0x8F, 0x2B, 0x87, + 0x62, 0x3D, 0x56, 0xE4, 0xFB, 0x91, 0xB5, 0x34, 0xF5, 0x7F, 0x3D, 0xB4, 0x44, 0xC6, 0x83, 0x7B, 0x4C, 0xDC, 0xA3, 0xA6, 0x47, 0x97, 0xFD, 0xC5, 0x2E, 0xC6, 0x70, 0xD6, 0xA1, 0x7B, 0x3F, 0xA1, + 0x97, 0x93, 0x02, 0x66, 0xD0, 0x3B, 0x4C, 0x0B, 0xEE, 0xE6, 0xEE, 0x27, 0xC1, 0xC4, 0x86, 0xFD, 0x22, 0xC3, 0xB2, 0x0E, 0xE1, 0x81, 0xE4, 0x2C, 0x71, 0x34, 0x70, 0x32, 0x8C, 0x14, 0x36, 0x23, + 0xA2, 0x53, 0xAA, 0xE0, 0xB1, 0x45, 0x3D, 0xA0, 0x09, 0xD8, 0xD4, 0xF2, 0x15, 0xD2, 0xF5, 0x77, 0xDD, 0xC9, 0xF8, 0x2D, 0xCB, 0x66, 0x9C, 0x9D, 0x99, 0xF1, 0x74, 0x48, 0x6C, 0x8A, 0x4D, 0x08, + 0x04, 0xD3, 0x42, 0xE8, 0xD3, 0x64, 0xF3, 0xB7, 0x36, 0x89, 0x94, 0x96, 0x31, 0xB2, 0x99, 0xD8, 0x73, 0x50, 0x15, 0xDB, 0x99, 0x70, 0x42, 0x07, 0xF0, 0x91, 0x4E, 0x6F, 0xCB, 0xF9, 0x21, 0xA1, + 0x8D, 0xF0, 0xC8, 0x08, 0x40, 0x45, 0x09, 0x28, 0x39, 0xCC, 0x96, 0xEA, 0xA5, 0xD2, 0xF6, 0xB6, 0x60, 0x00, 0x61, 0x6B, 0x7D, 0x2D, 0xED, 0x28, 0x5F, 0xF9, 0xA9, 0x24, 0x06, 0x81, 0x4A, 0x57, + 0xC2, 0x64, 0x68, 0xCC, 0x1D, 0x6C, 0x69, 0x47, 0x97, 0x63, 0x7B, 0x5B, 0xA5, 0x36, 0x4F, 0xD4, 0x60, 0x68, 0xCF, 0xE5, 0xC8, 0x22, 0xD2, 0xBB, 0xBD, 0xB3, 0x57, 0xC7, 0x6A, 0x36, 0x39, 0xAB, + 0x99, 0x96, 0x85, 0xED, 0x6D, 0x6D, 0x3A, 0xFE, 0x6B, 0x48, 0xB8, 0x0C, 0x87, 0x01, 0x26, 0x60, 0xD9, 0x6F, 0x75, 0x1C, 0x11, 0x1C, 0x9F, 0x4A, 0x0D, 0x30, 0xA0, 0x60, 0xAF, 0x55, 0x43, 0x5D, + 0xB3, 0x38, 0x97, 0xE6, 0x09, 0x1E, 0x6E, 0x02, 0xD0, 0x85, 0x66, 0xF0, 0x90, 0xE6, 0xEE, 0xA4, 0x31, 0x04, 0x8D, 0x8D, 0xB9, 0xC9, 0xC4, 0x98, 0x5A, 0x2A, 0x81, 0x14, 0xC9, 0xFF, 0x35, 0xCA, + 0x39, 0x72, 0x33, 0x14, 0x98, 0x5D, 0x93, 0x96, 0x15, 0x4D, 0xE5, 0xC2, 0x95, 0xC9, 0xE6, 0x35, 0xB3, 0x1A, 0x4D, 0x23, 0x4B, 0x79, 0xE0, 0xE8, 0x04, 0xB3, 0xFE, 0x11, 0xCD, 0xD2, 0x99, 0xEE, + 0x77, 0xE7, 0x2E, 0x16, 0xD4, 0x26, 0x3B, 0xFC, 0x4C, 0xF8, 0x97, 0x21, 0xAB, 0x5E, 0x9B, 0xBC, 0x64, 0xFF, 0xA8, 0xDE, 0xC4, 0x52, 0x0D, 0xCB, 0x5E, 0x88, 0x81, 0xF3, 0x61, 0xCD, 0x18, 0xF2, + 0x13, 0x9C, 0x8C, 0xB4, 0x2A, 0x4D, 0x67, 0xFD, 0x7F, 0xA4, 0x27, 0x63, 0x56, 0xB4, 0xC3, 0x9B, 0xC2, 0x63, 0x23, 0x4E, 0xA6, 0xA9, 0xCA, 0xBC, 0xE7, 0x2D, 0x86, 0xF4, 0xEF, 0x36, 0x44, 0x82, + 0x05, 0x02, 0x3F, 0x62, 0xCC, 0x4D, 0xE6, 0x19, 0xF5, 0x57, 0x26, 0x87, 0x13, 0x89, 0xB3, 0x05, 0xEE, 0x54, 0x5E, 0x69, 0x29, 0xDF, 0x24, 0x2F, 0xDF, 0xA8, 0xF9, 0x9B, 0x3F, 0x9C, 0xBF, 0x86, + 0x21, 0x0A, 0xD1, 0x15, 0x4A, 0x64, 0xF2, 0x79, 0x99, 0x51, 0x52, 0xCC, 0x39, 0xB0, 0x17, 0xE4, 0x58, 0x95, 0xE7, 0xC0, 0xF8, 0xBC, 0xA0, 0xE1, 0xD9, 0xF2, 0x94, 0xE1, 0xE0, 0x63, 0xCF, 0xDC, + 0x9A, 0xE0, 0xC7, 0x37, 0x57, 0x90, 0x48, 0x2E, 0x5B, 0xB0, 0xFD, 0x67, 0xB7, 0xA1, 0xAC, 0xA1, 0x6A, 0xB1, 0xDD, 0xB3, 0xE3, 0x8B, 0xE9, 0x2C, 0x9D, 0x76, 0xA7, 0x99, 0xC7, 0x94, 0x7C, 0xB6, + 0xD7, 0x75, 0xBD, 0xFD, 0x85, 0x93, 0x50, 0xBF, 0x85, 0x89, 0x0A, 0x37, 0xD8, 0x8E, 0xA1, 0x60, 0x6A, 0xDE, 0x48, 0x03, 0xF0, 0x75, 0xEB, 0x1A, 0x13, 0x04, 0xF0, 0xF7, 0xBA, 0xDA, 0xFF, 0xF4, + 0x4D, 0xA2, 0xC7, 0xF9, 0x32, 0xB2, 0x5F, 0x2D, 0xAA, 0x9B, 0xCD, 0xCF, 0x0C, 0xB8, 0x42, 0x77, 0xAB, 0xC2, 0xCB, 0xF6, 0xA7, 0x1C, 0x1C, 0xED, 0xE8, 0x79, 0xAA, 0x0D, 0x0C, 0x56, 0xE0, 0xE0, + 0x40, 0x91, 0xBE, 0xD2, 0x3F, 0x22, 0x3D, 0x66, 0xF7, 0x3C, 0x77, 0x10, 0x49, 0x64, 0x44, 0xBE, 0x4E, 0x39, 0x5F, 0x46, 0xCA, 0xA8, 0x34, 0x79, 0x51, 0xB2, 0xB1, 0xF0, 0xD1, 0x87, 0x4F, 0x31, + 0x78, 0xE1, 0xE3, 0x20, 0xA9, 0x18, 0x17, 0xBD, 0xCE, 0x17, 0x8F, 0x64, 0x9D, 0x68, 0xB1, 0x4D, 0x55, 0x9F, 0x06, 0x74, 0x3F, 0xA7, 0xCC, 0x74, 0x35, 0x2E, 0xF2, 0x27, 0x50, 0x34, 0x34, 0x8D, + 0x75, 0x55, 0x6E, 0x49, 0xEA, 0xA2, 0xF9, 0xC7, 0xDA, 0xA9, 0xBC, 0x3F, 0x32, 0x8D, 0x2F, 0x4E, 0x65, 0x78, 0xA6, 0xE4, 0xC4, 0xA4, 0x73, 0x2F, 0xB0, 0x04, 0x25, 0x22, 0x9E, 0xEC, 0x97, 0xD1, + 0x40, 0xB7, 0xEC, 0x1E, 0x4A, 0x1C, 0xED, 0x27, 0xB7, 0x72, 0xD9, 0x99, 0x10, 0xFE, 0x1E, 0x28, 0xD2, 0x5B, 0xA9, 0x9F, 0xC2, 0x56, 0xF3, 0xAA, 0xD1, 0x9C, 0x1D, 0x55, 0x9A, 0x4B, 0xD8, 0xA4, + }, + .t1_len = 1280, + .t1 = { + 0x2D, 0xD6, 0x04, 0xD5, 0x36, 0x57, 0x11, 0xDA, 0xA1, 0xAF, 0xD0, 0x6E, 0x8E, 0xAF, 0x68, 0x7C, 0x39, 0x99, 0x62, 0x4D, 0x3C, 0x18, 0x10, 0x84, 0xA0, 0x72, 0x73, 0xB5, 0x5E, 0xF3, 0xA8, 0x4C, + 0x60, 0x98, 0x70, 0x3E, 0xCF, 0x97, 0xF7, 0xD4, 0x64, 0xC6, 0x52, 0x17, 0xAB, 0x2D, 0x5D, 0x34, 0x89, 0x35, 0x3C, 0x3E, 0x2B, 0x17, 0x27, 0x24, 0x55, 0xB0, 0x8A, 0x92, 0x18, 0x0B, 0xBC, 0x9E, + 0xCB, 0x88, 0x16, 0xC5, 0x4D, 0x98, 0x80, 0x01, 0x34, 0xB2, 0x38, 0xE0, 0x15, 0x84, 0xC1, 0x07, 0x7C, 0xAB, 0x47, 0x12, 0x83, 0x80, 0xD9, 0x26, 0x34, 0xCB, 0x29, 0x1E, 0x95, 0x8A, 0x62, 0xAC, + 0x22, 0xF0, 0x50, 0x1C, 0xFF, 0x04, 0x7A, 0xB9, 0x75, 0x6D, 0x58, 0xE2, 0xC4, 0x6C, 0xA1, 0xCB, 0xED, 0xC6, 0x11, 0x85, 0x72, 0x1F, 0xE0, 0x0D, 0xAF, 0xFC, 0x5E, 0xFD, 0xFD, 0x40, 0xE2, 0xD4, + 0x5F, 0x06, 0x8A, 0xD1, 0x8C, 0x42, 0xCD, 0xDC, 0x6C, 0x26, 0xF0, 0x42, 0xFB, 0xBA, 0xF8, 0xDE, 0x52, 0x4B, 0xF1, 0x0C, 0x5E, 0x56, 0xA6, 0x36, 0x9F, 0xCB, 0xF7, 0x41, 0x4B, 0xA8, 0x51, 0xD7, + 0x54, 0x6C, 0x0A, 0xDB, 0xA0, 0xDD, 0xDE, 0x66, 0xA9, 0x85, 0x2F, 0x05, 0xB8, 0x12, 0xFC, 0xCB, 0x66, 0xCA, 0x7A, 0x0E, 0xD2, 0xC5, 0xBD, 0x36, 0x55, 0xBF, 0xD8, 0xAA, 0x4B, 0xEF, 0xB8, 0x63, + 0xFC, 0xEE, 0xE2, 0xEB, 0x4F, 0x66, 0x81, 0xC7, 0x5A, 0x75, 0xD4, 0x2C, 0xA4, 0x60, 0x01, 0x6B, 0x98, 0xA7, 0x75, 0x11, 0x4C, 0xC8, 0x37, 0x6C, 0x74, 0x2B, 0xD7, 0x20, 0x2F, 0x81, 0xE3, 0x7E, + 0xAB, 0xA9, 0xE4, 0x37, 0x8B, 0x7B, 0xD3, 0xF0, 0xED, 0xBA, 0x40, 0xAA, 0xB7, 0x15, 0xD4, 0x5E, 0x66, 0x63, 0xC9, 0x9B, 0xE6, 0x34, 0x38, 0xB9, 0x58, 0x36, 0x8C, 0xB2, 0x3F, 0x42, 0xF5, 0x4E, + 0xBC, 0xDC, 0xDA, 0x4F, 0x85, 0x70, 0xCA, 0xFE, 0x2E, 0xA1, 0x72, 0x8C, 0x0B, 0x23, 0xD9, 0xBB, 0x22, 0xFA, 0xB6, 0x92, 0x2E, 0xA6, 0x69, 0x4D, 0x7F, 0xDF, 0xCA, 0x08, 0xC7, 0x7E, 0xD4, 0x88, + 0xAC, 0x5F, 0xEF, 0xDC, 0xA7, 0x88, 0x9E, 0xE4, 0xED, 0x5F, 0xDA, 0xA7, 0xA1, 0x26, 0xDC, 0xA6, 0xD5, 0xEF, 0x6C, 0x43, 0xBF, 0x35, 0xB6, 0x12, 0x2E, 0x6E, 0xF0, 0xE5, 0x81, 0xAC, 0x33, 0x82, + 0x38, 0xE5, 0x14, 0xAA, 0x3A, 0xA9, 0x62, 0x48, 0xEB, 0x6D, 0x58, 0x38, 0xD3, 0x41, 0x74, 0x12, 0x75, 0x82, 0x33, 0xA0, 0x5C, 0x56, 0xEC, 0x4B, 0x5C, 0x5F, 0x1B, 0x59, 0x22, 0x5E, 0x53, 0xEE, + 0x2D, 0xA1, 0xF8, 0x32, 0x6C, 0x50, 0xE6, 0x98, 0x8B, 0xF6, 0x14, 0x58, 0x7F, 0x37, 0xBE, 0xA8, 0x7B, 0xF4, 0x57, 0x15, 0x46, 0x34, 0xCC, 0xF3, 0xE7, 0xE9, 0xA6, 0xD1, 0x59, 0x04, 0x92, 0x51, + 0x80, 0xDB, 0xE0, 0xEA, 0x7B, 0x2B, 0xDA, 0x61, 0x5A, 0x4D, 0xE6, 0xE8, 0x3A, 0x48, 0x47, 0xD6, 0x0A, 0xC4, 0xAC, 0x7F, 0x80, 0xA9, 0x3D, 0xC6, 0xBE, 0x06, 0xA4, 0x80, 0x10, 0x21, 0xFE, 0x7C, + 0x71, 0x78, 0x58, 0xF5, 0x64, 0x8A, 0x5E, 0x53, 0x87, 0x0C, 0x6D, 0x42, 0xB7, 0x7D, 0x29, 0x89, 0x0E, 0xB5, 0x45, 0x65, 0x7B, 0x7A, 0xF6, 0xE1, 0x40, 0xA7, 0xE1, 0x4B, 0x88, 0xD3, 0x1D, 0xC0, + 0x72, 0xCD, 0x9A, 0x41, 0xC6, 0x6B, 0xB2, 0xC7, 0x08, 0x9F, 0x4F, 0x16, 0x7B, 0xA0, 0xDD, 0xF9, 0x08, 0xAD, 0x7A, 0x2A, 0xB0, 0xCE, 0x19, 0xCC, 0x4A, 0x17, 0x7E, 0x0C, 0xF1, 0x2C, 0x8A, 0xFE, + 0xC9, 0x85, 0x8C, 0x39, 0x24, 0x73, 0x8F, 0x04, 0xDD, 0xDF, 0xDA, 0xF8, 0x53, 0xF7, 0xED, 0xCB, 0xE5, 0x2F, 0xCA, 0xF3, 0xE3, 0x82, 0xC7, 0x12, 0xC4, 0xE8, 0x21, 0xC2, 0x4D, 0xF9, 0x1D, 0x15, + 0x73, 0xA7, 0x4C, 0xE2, 0x1E, 0x44, 0xEF, 0xBA, 0x8A, 0x8E, 0xC6, 0xE6, 0xD5, 0xEE, 0x0B, 0xD8, 0xEB, 0xE0, 0x24, 0x36, 0x62, 0x35, 0x72, 0x35, 0x3E, 0x42, 0x10, 0xCB, 0x84, 0xD1, 0x28, 0x3E, + 0x1F, 0x6B, 0xA7, 0x26, 0xB2, 0x74, 0x6E, 0xB4, 0x36, 0x2D, 0x46, 0x4C, 0xF2, 0xE2, 0x78, 0xB2, 0xC4, 0x35, 0x68, 0xC9, 0xD7, 0x76, 0x14, 0xDD, 0xCA, 0x1B, 0x19, 0x3D, 0x3C, 0xCA, 0x67, 0xFC, + 0x7B, 0x4B, 0x41, 0x17, 0xD1, 0xFE, 0x2D, 0x17, 0x80, 0xEF, 0x90, 0x53, 0x8A, 0xFA, 0xEA, 0xDF, 0xB3, 0x76, 0xE3, 0x18, 0x33, 0x0E, 0x78, 0x5A, 0xF1, 0x03, 0x75, 0x3F, 0xD5, 0x99, 0x17, 0xBA, + 0xBB, 0xC0, 0xC8, 0xD7, 0x53, 0x2E, 0x0A, 0x54, 0xBF, 0x8E, 0x91, 0xF4, 0xAA, 0xAA, 0xDC, 0x9D, 0x53, 0x51, 0x3A, 0x04, 0xA1, 0xB5, 0x30, 0xD7, 0x11, 0xC4, 0x04, 0x69, 0x06, 0x3A, 0xB2, 0xFB, + 0xF5, 0xEA, 0xEB, 0x2A, 0x94, 0x1A, 0x58, 0x12, 0x6E, 0xB5, 0x80, 0x2D, 0x1A, 0x97, 0xD4, 0x4B, 0xF3, 0x40, 0x82, 0xB0, 0x26, 0x41, 0x0A, 0x83, 0xD4, 0x2D, 0xFB, 0x4C, 0x5D, 0xD1, 0xDB, 0xA8, + 0xC1, 0x9D, 0x33, 0xDD, 0x53, 0xB6, 0x1A, 0x7B, 0x58, 0x6A, 0xA0, 0x6D, 0xC4, 0x41, 0x4B, 0xB4, 0xC5, 0x3F, 0x26, 0xE0, 0x5A, 0x69, 0xCB, 0x71, 0x9C, 0xFD, 0xCE, 0x1E, 0x27, 0x29, 0x77, 0xC5, + 0x26, 0xCF, 0xC1, 0xB3, 0xA7, 0x24, 0x82, 0xAA, 0x24, 0x61, 0xF1, 0xC4, 0x67, 0x24, 0xF2, 0xD9, 0xCA, 0x9D, 0x31, 0xF9, 0x3E, 0x9D, 0x3C, 0x55, 0xD9, 0x44, 0xA5, 0x6D, 0xB9, 0x47, 0x0E, 0x45, + 0x41, 0xE2, 0x17, 0xC8, 0x02, 0xC1, 0x9A, 0x2F, 0x93, 0x23, 0xEF, 0xB5, 0x8F, 0x62, 0xCA, 0xF6, 0xFA, 0x86, 0x06, 0x1D, 0xD8, 0x8A, 0x89, 0xF0, 0x82, 0x71, 0x31, 0x8D, 0xE8, 0xA8, 0x1A, 0x56, + 0x65, 0x64, 0x33, 0x20, 0x10, 0xFF, 0xE4, 0xC8, 0x8A, 0x2A, 0x02, 0x26, 0x51, 0xAA, 0x32, 0xF5, 0x73, 0xB3, 0xB1, 0x54, 0xAA, 0x8C, 0xF1, 0x0D, 0xFB, 0xDC, 0xC0, 0xC5, 0x7B, 0x23, 0x41, 0xCF, + 0x9D, 0x6E, 0x5F, 0xDA, 0x17, 0xA7, 0xA3, 0x61, 0x6D, 0x24, 0x24, 0xCA, 0x2B, 0x9F, 0xE0, 0x8D, 0xC6, 0xC2, 0x96, 0xDF, 0xA2, 0xBE, 0x9D, 0xE8, 0xE5, 0x3C, 0x32, 0x8B, 0x8D, 0x66, 0x14, 0x2A, + 0xE2, 0x33, 0xEF, 0xA3, 0x0D, 0x90, 0xE9, 0x1A, 0x75, 0x78, 0x67, 0x56, 0xB8, 0xAB, 0x25, 0xC1, 0x5B, 0x91, 0xCF, 0x34, 0xA0, 0xE1, 0x2D, 0xAC, 0x9D, 0x5E, 0x52, 0x5A, 0xA5, 0x8D, 0x22, 0x9D, + 0x4E, 0x60, 0xDC, 0x2A, 0xB2, 0x7C, 0x61, 0x79, 0x0F, 0xAE, 0x21, 0x5C, 0x20, 0x05, 0x20, 0x21, 0x6C, 0xBB, 0x39, 0x8A, 0x20, 0x9B, 0x78, 0x4E, 0x31, 0xAF, 0x7E, 0x15, 0xF0, 0xA0, 0x07, 0x31, + 0x95, 0x74, 0x88, 0x7E, 0x6C, 0x27, 0x66, 0xA0, 0x40, 0x96, 0xAF, 0x1E, 0xDC, 0x45, 0x93, 0xF2, 0xFA, 0x91, 0x8F, 0x1A, 0x48, 0x51, 0xEF, 0x4C, 0xDB, 0x7A, 0xDD, 0xC4, 0x08, 0xDC, 0x3C, 0x57, + 0x91, 0x5C, 0x8B, 0xD9, 0x90, 0xC1, 0x00, 0x06, 0x16, 0x9D, 0x84, 0xFB, 0xDF, 0x13, 0xC7, 0x09, 0x7B, 0xEC, 0x77, 0xE3, 0xF1, 0x47, 0x57, 0x60, 0x23, 0x23, 0x2A, 0x74, 0x50, 0xF7, 0x86, 0x4F, + 0x21, 0xB3, 0x28, 0xAC, 0xBA, 0x0A, 0x4B, 0x21, 0x25, 0x6B, 0x1B, 0x08, 0xD4, 0xA4, 0xCD, 0x7A, 0xA5, 0x3A, 0x30, 0x7B, 0xC1, 0xAE, 0x36, 0x0D, 0x78, 0xE9, 0x3D, 0x43, 0x82, 0xBC, 0xD5, 0x83, + 0x6E, 0x30, 0x19, 0xF6, 0x7A, 0x1F, 0x5C, 0x39, 0xA3, 0x0E, 0x8E, 0x9F, 0xA7, 0xB9, 0x62, 0x2C, 0xFA, 0xD1, 0x1A, 0x50, 0xF2, 0xE4, 0xF1, 0x7D, 0xBE, 0x8F, 0xF2, 0x49, 0x8B, 0xEF, 0xCE, 0x52, + 0x8F, 0x24, 0x13, 0x14, 0x26, 0x38, 0xED, 0x76, 0x59, 0x5E, 0xA2, 0x5D, 0xDD, 0x6F, 0xA9, 0xAC, 0x4D, 0xF3, 0x62, 0xFD, 0xC1, 0xAA, 0x83, 0x64, 0x0A, 0x03, 0x39, 0x19, 0x4D, 0xDE, 0x83, 0x03, + 0x61, 0xA1, 0x2D, 0xD3, 0xF1, 0xBB, 0x83, 0xAA, 0x7B, 0x22, 0xC4, 0xD5, 0xFC, 0x7A, 0x69, 0xFA, 0xEB, 0xEB, 0xC4, 0x80, 0xEE, 0x83, 0xE8, 0x0B, 0x62, 0xD7, 0xBB, 0x68, 0xFF, 0xAC, 0xBC, 0xAA, + 0xB2, 0xE4, 0x8F, 0xE8, 0x1F, 0x20, 0x9B, 0xD9, 0x24, 0x91, 0x51, 0xB2, 0x55, 0x2F, 0xFA, 0x3E, 0x5D, 0x79, 0xFF, 0x54, 0x13, 0xC9, 0x4E, 0x6F, 0xF7, 0x69, 0xDE, 0xB9, 0x7B, 0x29, 0x08, 0xDC, + 0xDC, 0x83, 0x6E, 0xC7, 0x0B, 0xFF, 0xE8, 0xF7, 0x07, 0x8E, 0xEB, 0x14, 0x44, 0x0E, 0x01, 0x40, 0xFB, 0x22, 0xE0, 0x25, 0xBC, 0x1A, 0x10, 0x32, 0x67, 0xF9, 0xEA, 0x89, 0x71, 0x06, 0x34, 0x72, + 0xB3, 0x39, 0x49, 0xAD, 0x2A, 0x15, 0xC1, 0x74, 0x02, 0x51, 0x31, 0x00, 0x20, 0x8D, 0x72, 0x60, 0x97, 0x18, 0x2F, 0xA1, 0x01, 0xFC, 0x38, 0xC5, 0xC4, 0x81, 0x6A, 0x3A, 0xBC, 0xCF, 0x9E, 0x44, + 0xBF, 0x3F, 0x2D, 0x63, 0x4D, 0xA9, 0xBE, 0xC7, 0x67, 0x97, 0x71, 0x49, 0x14, 0x85, 0x21, 0x3D, 0xD6, 0x25, 0xB3, 0x27, 0xD5, 0x3F, 0xF4, 0xED, 0x21, 0xE1, 0xFF, 0x19, 0xE5, 0xD6, 0xC0, 0x44, + 0x7F, 0x77, 0xBB, 0xED, 0xF3, 0xF3, 0x7C, 0x63, 0x7A, 0x18, 0x5F, 0xFC, 0x18, 0xA5, 0xEF, 0xCA, 0x43, 0x77, 0xE3, 0x48, 0x6C, 0xED, 0xF5, 0x8A, 0x03, 0xDB, 0x4B, 0x02, 0x3C, 0xF5, 0x17, 0xE1, + 0x1D, 0x80, 0xE8, 0xE2, 0x93, 0x54, 0x40, 0x20, 0xA4, 0xFA, 0xB7, 0x80, 0x9D, 0x32, 0xCB, 0xF0, 0x15, 0x1F, 0xF2, 0x3C, 0xC1, 0xB2, 0xC4, 0xBD, 0x0E, 0x41, 0x07, 0xC5, 0xC0, 0xD2, 0x72, 0x2E, + }, + .pkcs8_len = 0, + .spki_len = 0, + .msg_len = 66, + .msg = { + 0x22, 0x5D, 0x5C, 0xE2, 0xCE, 0xAC, 0x61, 0x93, 0x0A, 0x07, 0x50, 0x3F, 0xB5, 0x9F, 0x7C, 0x2F, 0x93, 0x6A, 0x3E, 0x07, 0x54, 0x81, 0xDA, 0x3C, 0xA2, 0x99, 0xA8, 0x0F, 0x8C, 0x5D, 0xF9, 0x22, + 0x3A, 0x07, 0x3E, 0x7B, 0x90, 0xE0, 0x2E, 0xBF, 0x98, 0xCA, 0x22, 0x27, 0xEB, 0xA3, 0x8C, 0x1A, 0xB2, 0x56, 0x82, 0x09, 0xE4, 0x6D, 0xBA, 0x96, 0x18, 0x69, 0xC6, 0xF8, 0x39, 0x83, 0xB1, 0x7D, + 0xCD, 0x49, + }, + .sig_len = 2420, + .sig = { + 0xB5, 0xF8, 0x9A, 0xE9, 0x07, 0x73, 0xF4, 0x9F, 0xB0, 0xAE, 0xFA, 0xFA, 0x2E, 0x5A, 0xC9, 0x5D, 0xB6, 0x5E, 0x53, 0x4A, 0x43, 0x1E, 0x7B, 0x64, 0x1F, 0xEE, 0x75, 0x1F, 0x89, 0x96, 0xC3, 0x67, + 0x17, 0xF3, 0xA8, 0x44, 0x7C, 0x99, 0x5D, 0x47, 0x5B, 0xC1, 0xC3, 0x40, 0x4A, 0xDF, 0x42, 0xE9, 0xFD, 0x89, 0x8B, 0x54, 0xED, 0x09, 0x9A, 0xB5, 0x4C, 0x5F, 0x47, 0x1B, 0xC7, 0xC4, 0xBB, 0x39, + 0x25, 0x30, 0xF8, 0x21, 0x05, 0x8D, 0xE4, 0xB2, 0xF4, 0x0E, 0xA7, 0xEF, 0x2A, 0x29, 0x7E, 0xC4, 0x0D, 0x65, 0x44, 0x67, 0x95, 0x48, 0x88, 0x55, 0x7D, 0x89, 0xC2, 0x2F, 0x79, 0xCB, 0x44, 0xCC, + 0x93, 0x11, 0xFF, 0x98, 0x7A, 0x9E, 0xE2, 0x61, 0x91, 0xE4, 0x27, 0xE9, 0xAF, 0x8F, 0xC8, 0x0F, 0xE7, 0x58, 0xFD, 0x4B, 0xB1, 0x88, 0x6D, 0x83, 0xB2, 0x30, 0x63, 0x4F, 0xD6, 0x5C, 0xE5, 0x3A, + 0x03, 0x69, 0x9E, 0xAB, 0xF3, 0x29, 0x20, 0x15, 0x78, 0x14, 0xC9, 0x7D, 0xEE, 0x6C, 0x48, 0x5C, 0x7E, 0x98, 0xA4, 0x31, 0x73, 0x26, 0xF5, 0xD6, 0x39, 0x9D, 0x73, 0xB3, 0x85, 0x5C, 0xEB, 0x17, + 0x77, 0x91, 0xE3, 0x39, 0x09, 0x3D, 0x62, 0xE6, 0x7D, 0x2C, 0x5B, 0x2E, 0x16, 0xAC, 0x2D, 0xCC, 0x0C, 0x54, 0x7D, 0x78, 0x19, 0xF1, 0xC0, 0xCF, 0x3F, 0xE7, 0x34, 0x61, 0x44, 0xA8, 0x9E, 0x87, + 0x5B, 0xA1, 0xCB, 0xC0, 0x75, 0x28, 0xFF, 0x75, 0xE5, 0x7C, 0x7E, 0x06, 0xDB, 0xE9, 0x96, 0x58, 0xB6, 0xAF, 0x15, 0xD9, 0x17, 0x37, 0x16, 0xBE, 0xD3, 0xFD, 0xEF, 0x7C, 0xEA, 0x4D, 0x33, 0x0C, + 0x31, 0xF6, 0x73, 0x37, 0x32, 0x53, 0xC5, 0x5A, 0x75, 0xA1, 0x14, 0xBC, 0xD0, 0x7F, 0x0C, 0xF5, 0x23, 0xDA, 0x09, 0xDC, 0x23, 0xAD, 0xCF, 0x8F, 0x82, 0x8A, 0xEB, 0xE8, 0x20, 0x79, 0x39, 0x41, + 0x5D, 0x0B, 0x0D, 0xCE, 0xDF, 0xFF, 0x1A, 0x04, 0xA4, 0xC2, 0x3B, 0xD5, 0x62, 0x13, 0x29, 0x20, 0xD6, 0xD3, 0xEA, 0x9F, 0x63, 0x3D, 0xBF, 0x48, 0x5C, 0x24, 0x6C, 0x0D, 0xC7, 0x6C, 0xF4, 0x09, + 0x80, 0xE3, 0x51, 0xA8, 0x8B, 0x19, 0xE9, 0x38, 0x5D, 0x98, 0x7A, 0xD9, 0xC5, 0x84, 0xC4, 0x25, 0xD3, 0x5D, 0xDB, 0x4D, 0xE7, 0x95, 0x6B, 0x8B, 0x12, 0xEF, 0x2B, 0xC1, 0x1A, 0x5C, 0xDA, 0x22, + 0xA7, 0xD3, 0x38, 0xD8, 0x10, 0x7C, 0x63, 0x79, 0x16, 0xCD, 0x9F, 0x8F, 0xB4, 0x04, 0xEB, 0x18, 0xB1, 0xB6, 0xCA, 0x08, 0xB5, 0xE9, 0xD3, 0x9C, 0xD4, 0x1F, 0xA8, 0xF0, 0xE1, 0x66, 0xE8, 0x12, + 0xD2, 0x34, 0x9F, 0x6A, 0x15, 0x65, 0x4A, 0xB7, 0x13, 0xC3, 0xEB, 0x19, 0x05, 0x6E, 0x02, 0xF9, 0x5B, 0x71, 0xB9, 0x18, 0xC6, 0x10, 0x9A, 0x39, 0x79, 0xC4, 0x66, 0x29, 0x0B, 0x0B, 0xCD, 0x4E, + 0xD5, 0x79, 0xC5, 0x08, 0x4F, 0x70, 0x5E, 0xF1, 0xA0, 0x21, 0x07, 0x59, 0x96, 0x89, 0xBE, 0xB4, 0xB3, 0xE0, 0x63, 0x0E, 0xC5, 0xCD, 0x7F, 0x3C, 0xE5, 0x8D, 0xF5, 0xEA, 0x60, 0x12, 0xE0, 0x9E, + 0x30, 0xB9, 0xDF, 0xF6, 0x5D, 0x0C, 0xD5, 0x5B, 0xCA, 0x59, 0xBE, 0xDB, 0xB2, 0xA4, 0x53, 0x68, 0x3D, 0x71, 0xA1, 0xD6, 0x99, 0x92, 0x76, 0x1D, 0xA4, 0xF6, 0xC2, 0xB3, 0x76, 0xA8, 0x7D, 0x7E, + 0x78, 0x03, 0xF7, 0xC2, 0xA9, 0x92, 0x7E, 0x4A, 0x56, 0x0B, 0xE5, 0xF8, 0x0A, 0xCA, 0x92, 0xF8, 0x28, 0xC9, 0x9A, 0x63, 0xD8, 0x2A, 0x3A, 0xAA, 0xCC, 0xC6, 0xD9, 0xBC, 0x7B, 0xC8, 0xC5, 0xF6, + 0x70, 0x6C, 0x05, 0x48, 0xF5, 0x11, 0x0A, 0xDF, 0x48, 0x64, 0xEC, 0x62, 0x01, 0xE7, 0xB2, 0x2A, 0x6C, 0x13, 0xB6, 0x7F, 0x12, 0xB7, 0xA0, 0x59, 0x8C, 0x98, 0xD6, 0xC2, 0x7E, 0x60, 0xD4, 0x81, + 0x0F, 0xD5, 0x16, 0x79, 0x95, 0xE6, 0x6E, 0x30, 0x77, 0x3B, 0xF7, 0xCB, 0x03, 0xF3, 0x53, 0x9E, 0xB8, 0xE7, 0x2B, 0x83, 0x84, 0x53, 0x4D, 0xEB, 0x7D, 0xB7, 0x2B, 0x84, 0x7D, 0xD5, 0xC6, 0x6D, + 0x02, 0xFB, 0x4E, 0x95, 0x05, 0xB0, 0x08, 0x41, 0x9C, 0x72, 0x23, 0x02, 0xA1, 0x55, 0x95, 0x7B, 0x79, 0x6B, 0xE8, 0x77, 0xCF, 0xDB, 0x17, 0xCB, 0x68, 0xEC, 0xFC, 0x59, 0x0C, 0x6F, 0x12, 0x58, + 0x34, 0x68, 0xCB, 0x45, 0x4C, 0x67, 0xBE, 0x3F, 0x2E, 0x86, 0x1A, 0x38, 0x9E, 0x6F, 0x20, 0x65, 0xDD, 0x2E, 0x4F, 0xBC, 0x1D, 0x4C, 0xDD, 0xC3, 0xAD, 0x1C, 0x9A, 0x31, 0x16, 0xEF, 0x31, 0xF6, + 0x0E, 0xD8, 0x55, 0x77, 0xAA, 0x2E, 0xE2, 0xEF, 0xF7, 0x21, 0x7D, 0xC0, 0xA1, 0x73, 0x4E, 0x01, 0x43, 0xCC, 0xDB, 0x34, 0x64, 0x23, 0x4E, 0xDE, 0xFE, 0xFA, 0x8D, 0x05, 0x61, 0xD1, 0xB2, 0xEC, + 0x9A, 0xA9, 0xE7, 0x8E, 0xC8, 0x2F, 0xB0, 0x59, 0xB3, 0xEE, 0xD3, 0x29, 0xD4, 0x00, 0x26, 0xAB, 0x73, 0x95, 0xC4, 0x2C, 0xA5, 0x98, 0xD3, 0x7E, 0x69, 0x72, 0x9C, 0x37, 0x3A, 0x07, 0xFE, 0x48, + 0xA1, 0x91, 0xB9, 0x1F, 0xF3, 0xC9, 0x62, 0xE2, 0x9D, 0x0C, 0x9C, 0x40, 0x53, 0x6B, 0xA7, 0xB6, 0x52, 0x20, 0x12, 0xA2, 0xEE, 0x48, 0x95, 0x64, 0x0F, 0x07, 0x42, 0xA6, 0xF2, 0x02, 0x89, 0xAB, + 0x8E, 0x6C, 0x60, 0x4C, 0x1C, 0x56, 0x9B, 0xBE, 0x1F, 0x6B, 0xC3, 0x44, 0x9F, 0x44, 0xFD, 0x1C, 0xA2, 0x51, 0xD2, 0xFF, 0x2C, 0xA4, 0x69, 0x23, 0x0F, 0x79, 0x12, 0x97, 0x75, 0xBF, 0xC7, 0x2D, + 0xBA, 0x91, 0x2F, 0xB7, 0xE9, 0x6A, 0x7F, 0x87, 0x5C, 0x90, 0xC6, 0x5C, 0xA6, 0xB9, 0x9D, 0x17, 0x28, 0xB7, 0x92, 0xE2, 0x71, 0x95, 0x16, 0x26, 0x5D, 0xCF, 0x90, 0x63, 0xCD, 0x70, 0x99, 0xC7, + 0x29, 0xF0, 0x42, 0x5A, 0xE7, 0x47, 0xF7, 0xE0, 0x26, 0xBF, 0x41, 0xFF, 0xCB, 0x32, 0xEC, 0x89, 0xEF, 0xAD, 0x91, 0x44, 0x88, 0x00, 0x38, 0xC5, 0x72, 0x0E, 0x54, 0xFE, 0xBD, 0x97, 0x33, 0x37, + 0xC0, 0x5D, 0x55, 0x7B, 0x74, 0x11, 0x2B, 0xF2, 0x31, 0x87, 0xCE, 0x41, 0xDE, 0x9C, 0xED, 0x15, 0x6F, 0x08, 0x43, 0x93, 0x81, 0x3A, 0xFB, 0x43, 0x3C, 0x29, 0x2E, 0xFB, 0x37, 0xF1, 0x37, 0xE6, + 0x00, 0x6A, 0x95, 0xAD, 0xCD, 0x58, 0x0E, 0x36, 0x72, 0x18, 0x1B, 0xE8, 0xD3, 0x09, 0x13, 0xCA, 0x87, 0xE0, 0x08, 0x06, 0xBF, 0x82, 0xA7, 0x50, 0x9F, 0xD2, 0x57, 0xA7, 0x75, 0x91, 0xF6, 0x7A, + 0x78, 0x0F, 0x26, 0x49, 0x9C, 0xC0, 0xE9, 0x3C, 0xB0, 0x42, 0x60, 0x00, 0x1D, 0xA3, 0x43, 0xC7, 0x89, 0x75, 0x2C, 0xC1, 0xA4, 0x38, 0x39, 0x8F, 0xE0, 0x48, 0xF1, 0x9B, 0x0D, 0x83, 0xD1, 0xAF, + 0x95, 0x60, 0xB9, 0x09, 0xCF, 0xFE, 0x13, 0x64, 0x15, 0x6F, 0x4B, 0x45, 0x62, 0xD1, 0x57, 0x5E, 0x32, 0xC7, 0x7F, 0x8F, 0x0A, 0x26, 0x7B, 0xE4, 0x3E, 0x83, 0x72, 0xEB, 0x4A, 0x59, 0x69, 0x5A, + 0x62, 0x5B, 0x84, 0xC2, 0x79, 0x5C, 0x72, 0x4A, 0xC2, 0x40, 0xFC, 0x81, 0xCC, 0x1F, 0x03, 0xE0, 0x10, 0x04, 0xF9, 0x82, 0x20, 0xF3, 0xB4, 0x9E, 0x1B, 0x89, 0x6B, 0x42, 0x20, 0x49, 0xD1, 0x5C, + 0x4E, 0x54, 0x80, 0xD2, 0xE6, 0xDA, 0xE9, 0xA7, 0xAD, 0x5E, 0x5B, 0xB4, 0xF3, 0x06, 0xEA, 0xFB, 0x6A, 0xA5, 0x16, 0x6D, 0xFB, 0x5A, 0xCF, 0x5E, 0x7F, 0xF0, 0x57, 0x3E, 0x35, 0x42, 0xCF, 0xEA, + 0xFE, 0x1E, 0xDB, 0x4F, 0x1E, 0x40, 0x5D, 0xD3, 0x16, 0x7A, 0x92, 0x8E, 0x30, 0xDC, 0xC6, 0x0E, 0xF8, 0x62, 0xB5, 0xA0, 0xDB, 0xCF, 0x00, 0x27, 0x8B, 0x03, 0x23, 0xEC, 0x6C, 0xBA, 0xE1, 0x4C, + 0x8D, 0x79, 0x9B, 0xCC, 0x31, 0x10, 0x89, 0x30, 0x12, 0xEA, 0x81, 0x7E, 0xA0, 0x6F, 0x85, 0x32, 0x87, 0x48, 0xDF, 0x00, 0x9B, 0x7D, 0xD3, 0x6C, 0x46, 0x65, 0x52, 0xC6, 0x3F, 0x55, 0x0A, 0xF2, + 0xD2, 0x36, 0x7A, 0x3C, 0x17, 0xF7, 0x86, 0x6F, 0xA2, 0x2F, 0x1C, 0x8F, 0x16, 0xD2, 0xCB, 0x9F, 0x9A, 0xD7, 0x9F, 0xAE, 0xD0, 0x1E, 0x61, 0xEB, 0x31, 0xB0, 0x0A, 0xFD, 0x17, 0xA9, 0x84, 0x43, + 0x5B, 0x1C, 0xA2, 0x7A, 0xE4, 0xBB, 0xC3, 0x42, 0x48, 0x2F, 0x24, 0x72, 0x45, 0x11, 0x18, 0xB2, 0x89, 0x7E, 0x6C, 0xF7, 0x50, 0xFC, 0x1F, 0x53, 0xAC, 0x80, 0x81, 0xA6, 0x98, 0x66, 0x28, 0x4E, + 0xEF, 0x08, 0x72, 0xAC, 0x3E, 0xB3, 0x42, 0x7A, 0x51, 0x55, 0xA1, 0x66, 0x06, 0xBC, 0x5D, 0x6D, 0x05, 0x06, 0xDC, 0x48, 0xF1, 0xEB, 0x3E, 0x85, 0xF7, 0x1F, 0xCA, 0x62, 0xD5, 0xD9, 0xD3, 0xAB, + 0xE3, 0xBB, 0x3E, 0x9B, 0x03, 0xC4, 0xEE, 0xF7, 0xB2, 0x69, 0xB5, 0xA8, 0x5E, 0xD3, 0xCB, 0x14, 0xCD, 0xED, 0x13, 0xC1, 0xAB, 0x92, 0x69, 0x41, 0x52, 0x2A, 0x5B, 0xED, 0x34, 0xB2, 0xBC, 0x33, + 0xC1, 0x17, 0x33, 0x14, 0x22, 0x23, 0xC4, 0x5D, 0x50, 0x55, 0x46, 0x27, 0x84, 0x00, 0xEA, 0x96, 0x96, 0xA4, 0xF4, 0x19, 0xCC, 0x80, 0xB1, 0x3F, 0xFC, 0x3D, 0xF5, 0xE0, 0xE6, 0x35, 0x41, 0x29, + 0x3B, 0x51, 0xCE, 0x00, 0x6A, 0xD0, 0xA5, 0x1C, 0xE9, 0x56, 0xFA, 0x3C, 0xF9, 0x05, 0xFF, 0x13, 0x19, 0x93, 0x76, 0x78, 0x18, 0x27, 0x8F, 0x21, 0x23, 0xF0, 0x9F, 0x42, 0x21, 0x21, 0x21, 0x46, + 0xFD, 0x06, 0xB7, 0x1D, 0xC1, 0x3D, 0xC2, 0x64, 0xCC, 0xC9, 0xE3, 0xDD, 0x94, 0x6E, 0xBE, 0xB9, 0xB4, 0x06, 0x56, 0x83, 0x81, 0x87, 0x33, 0xA9, 0x77, 0x54, 0xCC, 0x85, 0xBC, 0x86, 0x9B, 0x69, + 0x7B, 0x1B, 0x99, 0x01, 0x1C, 0x32, 0xEB, 0x6E, 0xC4, 0xFF, 0x8A, 0xE3, 0xF6, 0xFC, 0x4E, 0xEA, 0xED, 0x42, 0x84, 0x09, 0xC5, 0xB0, 0x34, 0x25, 0x7A, 0x0B, 0x96, 0xF0, 0x05, 0x73, 0x7D, 0x47, + 0x56, 0xE7, 0x7C, 0xA5, 0x44, 0xB9, 0x0E, 0x84, 0x1F, 0x8B, 0x47, 0xEE, 0x82, 0x04, 0xEA, 0x85, 0xE3, 0xCB, 0xA9, 0x14, 0xA0, 0x39, 0xCC, 0xD9, 0xCC, 0xD0, 0x60, 0x4F, 0x13, 0x78, 0x95, 0xB0, + 0x35, 0x29, 0x17, 0xDA, 0x69, 0x90, 0xB0, 0x1A, 0x87, 0xAB, 0x5B, 0xBE, 0xBD, 0x41, 0x20, 0x7C, 0x8E, 0x9A, 0x43, 0xCA, 0x10, 0x27, 0x9D, 0x7C, 0xA7, 0x09, 0xD6, 0x4D, 0x36, 0xCF, 0xA2, 0x2E, + 0xD5, 0x01, 0x34, 0xDE, 0x4B, 0xA3, 0x83, 0x49, 0x11, 0x64, 0x92, 0xD7, 0x4B, 0x23, 0x92, 0x08, 0xDF, 0xD1, 0x94, 0x84, 0xEA, 0xBC, 0xFE, 0x39, 0x9C, 0x98, 0x5C, 0xD0, 0xCB, 0xCF, 0xE4, 0x50, + 0x25, 0xD3, 0x55, 0x8E, 0xC9, 0xD3, 0x80, 0xAA, 0x29, 0xB1, 0xBE, 0x2E, 0x65, 0x46, 0x20, 0x93, 0xB7, 0x3A, 0xF6, 0x45, 0x77, 0x7A, 0x19, 0x2C, 0x0B, 0x47, 0x12, 0x06, 0xC1, 0x4F, 0xE2, 0xE4, + 0xDC, 0xD6, 0x11, 0x5B, 0x4C, 0x97, 0xEC, 0xB1, 0x28, 0x86, 0x4D, 0x2B, 0xA0, 0x31, 0xF1, 0x2B, 0x44, 0xF3, 0x86, 0x1B, 0x4D, 0xA5, 0x71, 0x4E, 0x78, 0xB4, 0xF7, 0xCC, 0x31, 0xB5, 0xC8, 0xB5, + 0x04, 0xD1, 0x91, 0x5E, 0x5D, 0xB8, 0x96, 0x60, 0xF4, 0xCD, 0x7A, 0x54, 0x57, 0x68, 0x36, 0x74, 0xBE, 0xB3, 0x1C, 0x09, 0x67, 0x9F, 0x30, 0xAE, 0xD2, 0x29, 0xCF, 0xE5, 0xEA, 0xC8, 0xF2, 0xF6, + 0x18, 0x41, 0x6B, 0x00, 0x9B, 0x17, 0xED, 0x3E, 0x95, 0x36, 0x9E, 0xD1, 0xFB, 0xC8, 0x4F, 0xD8, 0x11, 0xB9, 0x3B, 0xE7, 0x65, 0xC4, 0x3A, 0xD7, 0xE1, 0x31, 0x3F, 0x7C, 0x23, 0x36, 0x4C, 0xC5, + 0xA5, 0xCE, 0xD5, 0x25, 0x9A, 0x16, 0xD6, 0x99, 0xB7, 0xDC, 0x93, 0x8A, 0xF8, 0xAB, 0xF2, 0xB7, 0xF7, 0x22, 0x67, 0x76, 0xCD, 0xF8, 0x77, 0xD5, 0xA8, 0x3B, 0x22, 0x24, 0xCE, 0xDD, 0x49, 0x4A, + 0x40, 0x79, 0x15, 0x74, 0x7F, 0x9A, 0x26, 0x80, 0x41, 0xB7, 0x43, 0x9F, 0x1C, 0x49, 0xB8, 0x80, 0x51, 0xB1, 0x2D, 0x1F, 0x03, 0x9D, 0xBF, 0xA7, 0xBD, 0x0D, 0x4B, 0x83, 0xA6, 0x66, 0xA5, 0xD9, + 0xA3, 0x41, 0x86, 0x61, 0x36, 0xA6, 0xF6, 0xFE, 0xCF, 0xDD, 0xFA, 0x37, 0x94, 0xC5, 0x2B, 0xE1, 0x38, 0xC6, 0xAB, 0x66, 0x27, 0x0E, 0x37, 0xF0, 0x49, 0x0F, 0x39, 0x7C, 0x80, 0x61, 0xBD, 0x05, + 0xBC, 0x57, 0x55, 0x69, 0x78, 0xC0, 0x3E, 0x9A, 0x34, 0x60, 0xB4, 0xBC, 0x82, 0x4D, 0x3D, 0xB7, 0xF5, 0x1E, 0x37, 0x08, 0xF5, 0x06, 0x2B, 0x42, 0xF1, 0x61, 0x7A, 0x33, 0x39, 0xD7, 0x7B, 0x03, + 0x3A, 0xB6, 0x3A, 0xD0, 0x0E, 0xC0, 0xC7, 0xD1, 0xF0, 0x76, 0x50, 0xBD, 0x1E, 0x26, 0xB4, 0xDB, 0x37, 0x5E, 0xEB, 0x35, 0xAF, 0x5D, 0xC2, 0x26, 0xA7, 0x42, 0x4C, 0xF1, 0x19, 0x15, 0x32, 0x4A, + 0x96, 0x29, 0x5B, 0xA9, 0xCE, 0x3E, 0x94, 0xCA, 0x41, 0x16, 0x9D, 0x7F, 0x93, 0xE6, 0x50, 0xE1, 0x00, 0xE8, 0x63, 0xD2, 0x59, 0x2B, 0xDB, 0x0D, 0xC0, 0x3C, 0x3B, 0x12, 0x50, 0x69, 0xFB, 0x24, + 0x80, 0x9A, 0x27, 0x9A, 0xC6, 0xCE, 0x58, 0x1A, 0x7C, 0x8C, 0x94, 0xB6, 0x2B, 0x2E, 0x5F, 0x9A, 0x92, 0x00, 0x33, 0x4E, 0x07, 0x92, 0x4A, 0xE3, 0x8D, 0xF3, 0xF4, 0x0D, 0xB3, 0x91, 0x0C, 0x35, + 0xE6, 0xD5, 0xE7, 0xE9, 0x54, 0xC4, 0x4A, 0xC8, 0xE3, 0xBE, 0x20, 0xDB, 0x46, 0x99, 0x05, 0x74, 0x13, 0x02, 0x43, 0x1F, 0xB9, 0x75, 0xED, 0x1E, 0xDB, 0x26, 0x15, 0x26, 0x33, 0x28, 0xFF, 0x51, + 0xBA, 0xAC, 0x89, 0xFD, 0xAC, 0xAD, 0xAB, 0x5E, 0x79, 0xE5, 0xDE, 0x54, 0xCA, 0x24, 0xC1, 0xE3, 0x94, 0x32, 0x5A, 0xD8, 0x02, 0x34, 0x67, 0xB2, 0x3A, 0x8F, 0xF7, 0xEC, 0x22, 0x7E, 0x88, 0x32, + 0x7B, 0x97, 0x40, 0x8F, 0x8A, 0xD2, 0x3A, 0xFE, 0xA5, 0xF9, 0xA8, 0x1E, 0x39, 0x9B, 0x92, 0x79, 0xC2, 0xDE, 0x78, 0x77, 0x37, 0xAD, 0xF3, 0x83, 0xB4, 0x83, 0x58, 0x56, 0x8B, 0xA0, 0x4B, 0x41, + 0x24, 0x89, 0xBF, 0x78, 0xD6, 0x35, 0xC0, 0xA5, 0xDA, 0x0F, 0xED, 0xCD, 0xC0, 0xB7, 0xAF, 0xCB, 0x88, 0xF3, 0xB8, 0x35, 0x89, 0x4B, 0xD0, 0x38, 0x57, 0x32, 0x51, 0x37, 0xA4, 0x26, 0x4D, 0xBD, + 0x40, 0x12, 0x92, 0x6F, 0x9E, 0x8C, 0x3E, 0xC6, 0x21, 0x66, 0x99, 0x57, 0x41, 0x3E, 0xC5, 0x11, 0xCD, 0xCB, 0xB4, 0xA3, 0x1F, 0x3F, 0x60, 0x7D, 0x28, 0x9E, 0xEB, 0xEC, 0xCD, 0x86, 0xE9, 0x92, + 0x30, 0x31, 0x66, 0xE6, 0x0B, 0x8A, 0x12, 0x6C, 0xEF, 0x13, 0x90, 0x2D, 0x4A, 0xB1, 0x77, 0xFA, 0x23, 0xB0, 0xEC, 0x0D, 0x72, 0x6C, 0x59, 0x57, 0x67, 0x04, 0x58, 0xE3, 0x22, 0x53, 0x9B, 0xF0, + 0xFC, 0x19, 0x3E, 0xE5, 0x24, 0xDA, 0xBC, 0xEA, 0x6C, 0x74, 0x33, 0xFE, 0xDD, 0x56, 0x37, 0x87, 0x23, 0x76, 0xD9, 0xE4, 0x91, 0x8F, 0xF5, 0x51, 0xA6, 0xE0, 0xF4, 0x0C, 0x1A, 0xB7, 0x54, 0xDF, + 0x60, 0x6D, 0xE6, 0x45, 0xE3, 0xE7, 0x82, 0x0C, 0x85, 0x3F, 0xEE, 0xC0, 0x6A, 0x7D, 0x45, 0xCF, 0x87, 0x9F, 0x79, 0x07, 0x2C, 0x30, 0x59, 0x51, 0x52, 0xF2, 0x9E, 0xE3, 0xB3, 0xBA, 0x04, 0xAE, + 0x33, 0xA2, 0x87, 0x29, 0x80, 0xFC, 0x6D, 0xD7, 0xC2, 0x31, 0xC7, 0xFA, 0x34, 0x7C, 0xBD, 0x68, 0xD9, 0xB2, 0xEE, 0xF5, 0x78, 0x6E, 0x48, 0xF7, 0x8A, 0x8A, 0x28, 0x02, 0x50, 0x60, 0x90, 0x28, + 0x49, 0xCA, 0xC6, 0x70, 0x25, 0x83, 0xB1, 0x1D, 0x37, 0x67, 0x78, 0x68, 0x08, 0x1E, 0x06, 0xFC, 0x6A, 0x7E, 0xDF, 0xBE, 0x6B, 0x9C, 0xBB, 0xD2, 0xC7, 0x37, 0x0B, 0x29, 0x61, 0x70, 0x4B, 0x05, + 0xF3, 0x57, 0xFB, 0x46, 0x33, 0xA9, 0xEF, 0x6B, 0x2E, 0xFE, 0xB2, 0xD8, 0xFF, 0xA3, 0x1C, 0xC9, 0x0F, 0xC4, 0x51, 0x5A, 0x95, 0x3F, 0x8F, 0x7F, 0x68, 0x81, 0x93, 0x18, 0x71, 0x2E, 0x06, 0x44, + 0x09, 0x3A, 0x0A, 0x18, 0xE4, 0x31, 0xE4, 0x64, 0x28, 0x76, 0x31, 0x6C, 0xFC, 0x12, 0x7D, 0x67, 0x4B, 0x67, 0x6F, 0x29, 0xC9, 0x0C, 0x9D, 0x25, 0x14, 0x21, 0x49, 0x54, 0x17, 0xC0, 0xC1, 0xF0, + 0x96, 0xBC, 0x1C, 0xC8, 0xD6, 0xBF, 0xF1, 0x7F, 0x95, 0x3B, 0xF2, 0x48, 0x5D, 0x19, 0x50, 0xA0, 0x9D, 0x3C, 0x3A, 0x92, 0x88, 0xE6, 0xCE, 0xE2, 0x30, 0xCF, 0x41, 0xC3, 0x4B, 0x1F, 0x3B, 0xB8, + 0x33, 0x0A, 0x96, 0x07, 0xCB, 0x62, 0xA9, 0x51, 0x0F, 0xC2, 0x5A, 0x0E, 0x5F, 0x67, 0x0B, 0x48, 0x69, 0x3C, 0x06, 0xF8, 0xA0, 0x2C, 0x29, 0x7D, 0xBB, 0xAF, 0xE5, 0x67, 0x61, 0x86, 0x08, 0x29, + 0xE4, 0xB5, 0x5D, 0xF0, 0xC7, 0xE0, 0x06, 0x91, 0xB5, 0xE0, 0x88, 0xCE, 0xC8, 0x06, 0x78, 0x0B, 0xB3, 0xAB, 0x6C, 0x2C, 0x06, 0x8C, 0x4E, 0xD8, 0xFC, 0x47, 0xFE, 0x39, 0x76, 0xD1, 0x65, 0x1E, + 0x63, 0x0E, 0xCE, 0x0F, 0xA7, 0x7B, 0x5F, 0x05, 0xA6, 0xFE, 0x70, 0x20, 0x9D, 0x31, 0x86, 0x0C, 0xEB, 0x98, 0xFA, 0x49, 0xB7, 0xEC, 0x55, 0x25, 0x1A, 0xEB, 0x7C, 0x7C, 0x90, 0x16, 0xD1, 0x80, + 0x40, 0x5A, 0x1E, 0x5A, 0x24, 0x69, 0x15, 0x51, 0xCF, 0xE6, 0xFD, 0x8E, 0x8F, 0x36, 0x17, 0x90, 0x2B, 0xE0, 0xF6, 0x33, 0x53, 0xE7, 0x3F, 0x05, 0x46, 0x01, 0xF0, 0xCD, 0x2B, 0x1C, 0xE8, 0xBF, + 0xB2, 0x0B, 0x7C, 0x64, 0x9D, 0x31, 0xCE, 0x52, 0xC1, 0xB7, 0xEF, 0xDD, 0xE9, 0xD9, 0xD8, 0x6B, 0x39, 0x52, 0x18, 0x6C, 0xAF, 0x0C, 0x3C, 0xCE, 0x1F, 0xDD, 0x13, 0x04, 0x26, 0xE4, 0x2E, 0x02, + 0x09, 0x0F, 0x5B, 0x5D, 0x5E, 0x74, 0x75, 0x7B, 0x82, 0xA7, 0xB4, 0xC2, 0xCF, 0xDB, 0xE4, 0x10, 0x40, 0x43, 0x4E, 0x62, 0x66, 0x67, 0x69, 0x8B, 0x98, 0x9B, 0xA4, 0xB2, 0xD2, 0xE0, 0xE9, 0xF7, + 0x09, 0x21, 0x2A, 0x3B, 0x46, 0x52, 0x58, 0x71, 0x8E, 0xC0, 0xD7, 0xE1, 0xE6, 0xED, 0xF5, 0x10, 0x28, 0x32, 0x39, 0x4F, 0x56, 0x57, 0x78, 0x80, 0x8F, 0x9B, 0xAE, 0xB2, 0xDE, 0xEF, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0F, 0x20, 0x2F, 0x3E, + }, + }, + { + .name = "Dilithium Round 3, Level 3 (6-5) KAT 0 (PKCS#8/SPKI)", + .version = 0, + .keyform = 0, + .rho_len = 0, + .seed_len = 0, + .tr_len = 0, + .s1_len = 0, + .s2_len = 0, + .t0_len = 0, + .t1_len = 0, + .pkcs8_len = 5988, + .pkcs8 = { + 0x30, 0x82, 0x17, 0x60, 0x02, 0x01, 0x00, 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0B, 0x07, 0x06, 0x05, 0x05, 0x00, 0x04, 0x82, 0x17, 0x48, 0x30, 0x82, 0x17, 0x44, + 0x02, 0x01, 0x00, 0x03, 0x21, 0x00, 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, + 0x38, 0xD5, 0x06, 0xD8, 0x5B, 0xEF, 0x03, 0x21, 0x00, 0x39, 0x4D, 0x16, 0x95, 0x05, 0x9D, 0xFF, 0x40, 0xAE, 0x25, 0x6C, 0x5D, 0x5E, 0xDA, 0xBF, 0xB6, 0x9F, 0x5F, 0x40, 0xF3, 0x7A, 0x58, 0x8F, + 0x50, 0x53, 0x2C, 0xA4, 0x08, 0xA8, 0x16, 0x8A, 0xB1, 0x03, 0x21, 0x00, 0xE6, 0x4F, 0x14, 0x64, 0x27, 0x54, 0x3D, 0x8C, 0x36, 0xB3, 0xB6, 0x52, 0x26, 0x76, 0x9A, 0x22, 0x91, 0x1A, 0x5A, 0x31, + 0x3E, 0xAC, 0x17, 0xC4, 0xAB, 0xA2, 0x52, 0x84, 0x51, 0x4F, 0xC6, 0x13, 0x03, 0x82, 0x02, 0x81, 0x00, 0x35, 0x78, 0x08, 0x33, 0x02, 0x23, 0x16, 0x43, 0x37, 0x65, 0x80, 0x75, 0x78, 0x71, 0x45, + 0x24, 0x81, 0x01, 0x73, 0x15, 0x44, 0x83, 0x65, 0x26, 0x41, 0x33, 0x30, 0x22, 0x30, 0x26, 0x14, 0x73, 0x70, 0x52, 0x21, 0x07, 0x81, 0x26, 0x50, 0x61, 0x85, 0x85, 0x07, 0x75, 0x46, 0x18, 0x58, + 0x05, 0x48, 0x53, 0x30, 0x18, 0x70, 0x66, 0x47, 0x51, 0x82, 0x67, 0x73, 0x77, 0x33, 0x50, 0x02, 0x70, 0x31, 0x28, 0x78, 0x82, 0x15, 0x80, 0x71, 0x40, 0x26, 0x73, 0x43, 0x20, 0x61, 0x62, 0x50, + 0x61, 0x73, 0x71, 0x01, 0x03, 0x11, 0x45, 0x36, 0x81, 0x52, 0x30, 0x24, 0x65, 0x03, 0x48, 0x14, 0x37, 0x08, 0x37, 0x18, 0x25, 0x50, 0x84, 0x06, 0x08, 0x60, 0x17, 0x62, 0x58, 0x31, 0x31, 0x28, + 0x27, 0x00, 0x17, 0x18, 0x48, 0x16, 0x67, 0x31, 0x78, 0x61, 0x07, 0x37, 0x23, 0x55, 0x74, 0x47, 0x15, 0x10, 0x10, 0x11, 0x21, 0x10, 0x66, 0x27, 0x42, 0x12, 0x08, 0x35, 0x46, 0x22, 0x85, 0x13, + 0x13, 0x88, 0x16, 0x48, 0x86, 0x83, 0x35, 0x10, 0x47, 0x60, 0x26, 0x11, 0x83, 0x15, 0x74, 0x25, 0x00, 0x74, 0x24, 0x40, 0x64, 0x25, 0x15, 0x86, 0x13, 0x65, 0x61, 0x37, 0x77, 0x11, 0x84, 0x78, + 0x05, 0x08, 0x62, 0x43, 0x70, 0x64, 0x06, 0x85, 0x27, 0x63, 0x11, 0x50, 0x13, 0x56, 0x23, 0x21, 0x68, 0x41, 0x41, 0x77, 0x24, 0x08, 0x48, 0x30, 0x87, 0x85, 0x75, 0x43, 0x85, 0x08, 0x63, 0x68, + 0x54, 0x26, 0x84, 0x50, 0x56, 0x84, 0x37, 0x02, 0x40, 0x07, 0x16, 0x17, 0x84, 0x54, 0x38, 0x00, 0x61, 0x27, 0x05, 0x82, 0x62, 0x06, 0x76, 0x52, 0x11, 0x12, 0x14, 0x83, 0x88, 0x06, 0x78, 0x14, + 0x75, 0x55, 0x02, 0x12, 0x22, 0x85, 0x52, 0x31, 0x08, 0x45, 0x03, 0x70, 0x13, 0x64, 0x31, 0x80, 0x05, 0x37, 0x68, 0x37, 0x65, 0x02, 0x46, 0x53, 0x15, 0x07, 0x60, 0x06, 0x25, 0x33, 0x12, 0x51, + 0x20, 0x05, 0x41, 0x60, 0x63, 0x24, 0x23, 0x52, 0x41, 0x50, 0x77, 0x31, 0x45, 0x70, 0x33, 0x47, 0x65, 0x64, 0x31, 0x23, 0x18, 0x03, 0x33, 0x65, 0x16, 0x75, 0x87, 0x14, 0x13, 0x04, 0x11, 0x17, + 0x15, 0x54, 0x68, 0x12, 0x60, 0x53, 0x73, 0x42, 0x38, 0x82, 0x43, 0x27, 0x83, 0x37, 0x12, 0x22, 0x81, 0x74, 0x81, 0x81, 0x20, 0x13, 0x63, 0x27, 0x64, 0x75, 0x10, 0x28, 0x03, 0x22, 0x68, 0x65, + 0x08, 0x76, 0x55, 0x35, 0x63, 0x33, 0x81, 0x04, 0x47, 0x48, 0x58, 0x54, 0x30, 0x12, 0x43, 0x18, 0x08, 0x38, 0x64, 0x38, 0x53, 0x83, 0x08, 0x41, 0x27, 0x04, 0x64, 0x64, 0x63, 0x34, 0x64, 0x61, + 0x06, 0x80, 0x70, 0x60, 0x23, 0x75, 0x51, 0x68, 0x25, 0x74, 0x11, 0x52, 0x88, 0x22, 0x01, 0x57, 0x78, 0x58, 0x33, 0x31, 0x34, 0x31, 0x55, 0x82, 0x84, 0x03, 0x16, 0x36, 0x01, 0x06, 0x48, 0x14, + 0x80, 0x46, 0x43, 0x68, 0x46, 0x17, 0x57, 0x21, 0x36, 0x31, 0x65, 0x74, 0x65, 0x22, 0x15, 0x17, 0x71, 0x32, 0x05, 0x10, 0x66, 0x46, 0x83, 0x16, 0x46, 0x71, 0x47, 0x28, 0x31, 0x35, 0x55, 0x14, + 0x73, 0x32, 0x81, 0x82, 0x60, 0x73, 0x15, 0x54, 0x36, 0x87, 0x08, 0x03, 0x28, 0x43, 0x26, 0x24, 0x16, 0x05, 0x32, 0x05, 0x20, 0x23, 0x67, 0x72, 0x58, 0x28, 0x18, 0x10, 0x85, 0x42, 0x67, 0x85, + 0x15, 0x52, 0x80, 0x00, 0x72, 0x82, 0x27, 0x18, 0x31, 0x12, 0x08, 0x68, 0x37, 0x72, 0x44, 0x42, 0x05, 0x48, 0x64, 0x72, 0x05, 0x35, 0x08, 0x61, 0x73, 0x86, 0x27, 0x12, 0x46, 0x77, 0x51, 0x08, + 0x52, 0x76, 0x33, 0x40, 0x37, 0x34, 0x32, 0x11, 0x54, 0x24, 0x06, 0x54, 0x02, 0x34, 0x50, 0x80, 0x04, 0x17, 0x72, 0x84, 0x62, 0x73, 0x61, 0x68, 0x68, 0x07, 0x81, 0x52, 0x46, 0x71, 0x06, 0x82, + 0x55, 0x45, 0x81, 0x63, 0x62, 0x76, 0x41, 0x80, 0x57, 0x12, 0x44, 0x25, 0x57, 0x08, 0x04, 0x51, 0x06, 0x63, 0x61, 0x15, 0x85, 0x86, 0x30, 0x46, 0x52, 0x07, 0x05, 0x32, 0x75, 0x02, 0x18, 0x22, + 0x42, 0x83, 0x71, 0x02, 0x38, 0x52, 0x75, 0x28, 0x44, 0x20, 0x33, 0x00, 0x17, 0x23, 0x11, 0x14, 0x02, 0x15, 0x76, 0x88, 0x38, 0x47, 0x62, 0x31, 0x85, 0x13, 0x52, 0x52, 0x10, 0x84, 0x38, 0x25, + 0x55, 0x56, 0x74, 0x11, 0x44, 0x54, 0x67, 0x27, 0x85, 0x46, 0x58, 0x61, 0x70, 0x43, 0x07, 0x58, 0x80, 0x06, 0x84, 0x55, 0x13, 0x53, 0x47, 0x81, 0x38, 0x12, 0x08, 0x00, 0x84, 0x31, 0x56, 0x22, + 0x14, 0x66, 0x03, 0x15, 0x60, 0x01, 0x63, 0x68, 0x56, 0x36, 0x73, 0x61, 0x80, 0x80, 0x04, 0x55, 0x54, 0x03, 0x82, 0x03, 0x01, 0x00, 0x33, 0x73, 0x12, 0x58, 0x40, 0x31, 0x14, 0x80, 0x42, 0x03, + 0x67, 0x33, 0x01, 0x82, 0x71, 0x55, 0x60, 0x65, 0x60, 0x34, 0x40, 0x51, 0x44, 0x34, 0x55, 0x48, 0x51, 0x12, 0x23, 0x76, 0x45, 0x10, 0x64, 0x33, 0x73, 0x25, 0x38, 0x23, 0x38, 0x06, 0x24, 0x51, + 0x61, 0x70, 0x81, 0x54, 0x11, 0x67, 0x17, 0x32, 0x00, 0x85, 0x32, 0x60, 0x40, 0x43, 0x71, 0x06, 0x80, 0x37, 0x37, 0x60, 0x70, 0x86, 0x40, 0x87, 0x00, 0x03, 0x52, 0x45, 0x71, 0x48, 0x26, 0x22, + 0x03, 0x50, 0x53, 0x56, 0x66, 0x03, 0x72, 0x18, 0x01, 0x37, 0x10, 0x37, 0x10, 0x36, 0x52, 0x78, 0x43, 0x28, 0x24, 0x64, 0x23, 0x20, 0x47, 0x64, 0x23, 0x84, 0x00, 0x00, 0x67, 0x43, 0x64, 0x56, + 0x52, 0x26, 0x21, 0x76, 0x65, 0x21, 0x24, 0x13, 0x88, 0x73, 0x47, 0x65, 0x08, 0x43, 0x12, 0x17, 0x01, 0x64, 0x71, 0x46, 0x54, 0x03, 0x87, 0x24, 0x41, 0x77, 0x74, 0x13, 0x76, 0x78, 0x55, 0x21, + 0x64, 0x11, 0x17, 0x31, 0x60, 0x50, 0x48, 0x26, 0x04, 0x14, 0x84, 0x74, 0x66, 0x38, 0x03, 0x35, 0x15, 0x58, 0x01, 0x73, 0x51, 0x26, 0x21, 0x33, 0x62, 0x22, 0x27, 0x10, 0x63, 0x45, 0x60, 0x16, + 0x57, 0x20, 0x77, 0x85, 0x48, 0x32, 0x72, 0x48, 0x31, 0x56, 0x16, 0x78, 0x34, 0x56, 0x40, 0x57, 0x68, 0x67, 0x34, 0x58, 0x35, 0x25, 0x35, 0x20, 0x81, 0x55, 0x65, 0x48, 0x10, 0x32, 0x05, 0x33, + 0x40, 0x16, 0x60, 0x74, 0x23, 0x71, 0x50, 0x16, 0x32, 0x53, 0x34, 0x66, 0x72, 0x70, 0x81, 0x11, 0x18, 0x24, 0x37, 0x32, 0x13, 0x11, 0x54, 0x42, 0x40, 0x82, 0x61, 0x37, 0x75, 0x04, 0x67, 0x10, + 0x08, 0x02, 0x61, 0x38, 0x68, 0x50, 0x71, 0x28, 0x37, 0x52, 0x66, 0x72, 0x24, 0x23, 0x08, 0x02, 0x10, 0x05, 0x01, 0x55, 0x20, 0x48, 0x37, 0x44, 0x37, 0x71, 0x16, 0x42, 0x01, 0x23, 0x16, 0x71, + 0x07, 0x82, 0x38, 0x08, 0x07, 0x10, 0x11, 0x24, 0x68, 0x25, 0x82, 0x40, 0x18, 0x15, 0x85, 0x18, 0x74, 0x20, 0x85, 0x38, 0x25, 0x83, 0x10, 0x66, 0x75, 0x13, 0x12, 0x52, 0x85, 0x27, 0x65, 0x25, + 0x60, 0x31, 0x47, 0x81, 0x62, 0x13, 0x81, 0x53, 0x47, 0x04, 0x22, 0x61, 0x05, 0x71, 0x55, 0x67, 0x44, 0x68, 0x20, 0x05, 0x45, 0x50, 0x51, 0x48, 0x41, 0x13, 0x03, 0x83, 0x02, 0x41, 0x47, 0x47, + 0x15, 0x62, 0x72, 0x02, 0x16, 0x53, 0x21, 0x03, 0x03, 0x87, 0x36, 0x03, 0x48, 0x67, 0x51, 0x76, 0x65, 0x27, 0x21, 0x42, 0x17, 0x26, 0x25, 0x76, 0x65, 0x36, 0x12, 0x11, 0x12, 0x16, 0x87, 0x48, + 0x45, 0x40, 0x33, 0x42, 0x68, 0x35, 0x44, 0x40, 0x68, 0x13, 0x60, 0x50, 0x31, 0x08, 0x17, 0x43, 0x56, 0x75, 0x06, 0x34, 0x61, 0x84, 0x75, 0x57, 0x58, 0x58, 0x65, 0x44, 0x84, 0x07, 0x62, 0x31, + 0x86, 0x70, 0x34, 0x33, 0x67, 0x58, 0x66, 0x67, 0x73, 0x20, 0x75, 0x17, 0x10, 0x36, 0x05, 0x27, 0x37, 0x24, 0x12, 0x20, 0x17, 0x38, 0x87, 0x54, 0x40, 0x32, 0x26, 0x30, 0x62, 0x13, 0x54, 0x18, + 0x36, 0x81, 0x55, 0x77, 0x32, 0x00, 0x10, 0x03, 0x65, 0x18, 0x57, 0x41, 0x86, 0x02, 0x14, 0x44, 0x33, 0x41, 0x02, 0x37, 0x55, 0x63, 0x58, 0x75, 0x02, 0x61, 0x88, 0x64, 0x18, 0x51, 0x76, 0x24, + 0x15, 0x85, 0x07, 0x11, 0x80, 0x35, 0x41, 0x51, 0x57, 0x42, 0x42, 0x58, 0x54, 0x56, 0x35, 0x45, 0x15, 0x57, 0x07, 0x63, 0x86, 0x77, 0x24, 0x00, 0x17, 0x67, 0x83, 0x86, 0x86, 0x25, 0x88, 0x17, + 0x75, 0x08, 0x61, 0x23, 0x60, 0x60, 0x65, 0x07, 0x33, 0x35, 0x06, 0x60, 0x52, 0x75, 0x02, 0x47, 0x24, 0x33, 0x64, 0x51, 0x35, 0x45, 0x52, 0x55, 0x41, 0x48, 0x60, 0x42, 0x16, 0x43, 0x15, 0x63, + 0x33, 0x16, 0x55, 0x67, 0x60, 0x70, 0x34, 0x26, 0x77, 0x08, 0x07, 0x60, 0x55, 0x30, 0x63, 0x50, 0x13, 0x37, 0x70, 0x77, 0x01, 0x37, 0x45, 0x72, 0x74, 0x51, 0x28, 0x72, 0x83, 0x64, 0x74, 0x77, + 0x80, 0x27, 0x30, 0x36, 0x44, 0x23, 0x10, 0x55, 0x24, 0x15, 0x43, 0x11, 0x63, 0x14, 0x65, 0x33, 0x63, 0x12, 0x11, 0x84, 0x63, 0x12, 0x63, 0x88, 0x37, 0x62, 0x67, 0x48, 0x35, 0x13, 0x86, 0x35, + 0x17, 0x83, 0x12, 0x58, 0x14, 0x47, 0x88, 0x56, 0x08, 0x48, 0x01, 0x42, 0x71, 0x64, 0x77, 0x53, 0x64, 0x73, 0x54, 0x66, 0x05, 0x56, 0x60, 0x52, 0x37, 0x00, 0x46, 0x40, 0x31, 0x10, 0x55, 0x50, + 0x45, 0x36, 0x48, 0x42, 0x34, 0x06, 0x61, 0x11, 0x75, 0x52, 0x61, 0x58, 0x52, 0x15, 0x73, 0x57, 0x31, 0x56, 0x15, 0x87, 0x78, 0x74, 0x45, 0x03, 0x87, 0x20, 0x54, 0x56, 0x11, 0x66, 0x22, 0x04, + 0x46, 0x14, 0x14, 0x61, 0x83, 0x00, 0x06, 0x86, 0x64, 0x06, 0x00, 0x47, 0x37, 0x44, 0x22, 0x50, 0x56, 0x01, 0x04, 0x57, 0x73, 0x50, 0x74, 0x87, 0x02, 0x66, 0x37, 0x48, 0x68, 0x48, 0x02, 0x63, + 0x28, 0x52, 0x63, 0x58, 0x11, 0x30, 0x44, 0x28, 0x68, 0x32, 0x61, 0x10, 0x61, 0x88, 0x26, 0x07, 0x00, 0x73, 0x38, 0x62, 0x55, 0x27, 0x15, 0x53, 0x45, 0x32, 0x14, 0x25, 0x73, 0x23, 0x12, 0x21, + 0x87, 0x86, 0x55, 0x67, 0x25, 0x67, 0x46, 0x74, 0x72, 0x81, 0x44, 0x54, 0x64, 0x15, 0x77, 0x41, 0x07, 0x80, 0x60, 0x56, 0x13, 0x16, 0x15, 0x40, 0x44, 0x63, 0x47, 0x53, 0x30, 0x77, 0x61, 0x62, + 0x50, 0x13, 0x38, 0x41, 0x47, 0x42, 0x66, 0x70, 0x52, 0x06, 0x70, 0x81, 0x25, 0x43, 0x17, 0x77, 0x70, 0x15, 0x22, 0x21, 0x82, 0x50, 0x03, 0x82, 0x09, 0xC1, 0x00, 0x01, 0x31, 0x73, 0x16, 0x9D, + 0xB8, 0x08, 0x6B, 0x12, 0x27, 0x01, 0x70, 0x6A, 0xE4, 0x9B, 0x99, 0x30, 0x5E, 0xE6, 0xD0, 0x16, 0xF1, 0x6F, 0x9F, 0xAC, 0xC1, 0xF8, 0x35, 0x29, 0x8B, 0x41, 0xE2, 0x16, 0x64, 0x20, 0x60, 0x05, + 0xCE, 0xB9, 0x81, 0xA3, 0x5F, 0x18, 0x65, 0x1C, 0xDB, 0x90, 0xE6, 0x8C, 0x1F, 0x95, 0x0B, 0x05, 0x9F, 0x73, 0xD6, 0xD3, 0x14, 0x3A, 0x1F, 0x47, 0xAA, 0x21, 0xD8, 0x0A, 0x05, 0xFA, 0xF5, 0xD3, + 0xA4, 0x0F, 0x67, 0x14, 0x8D, 0x3A, 0x89, 0xA9, 0xFD, 0xA8, 0x03, 0x64, 0xD5, 0x7C, 0x7B, 0x8F, 0x68, 0x05, 0x8A, 0x25, 0xD0, 0x84, 0x98, 0xD9, 0xA9, 0xC3, 0x78, 0xC9, 0x81, 0x85, 0xDB, 0x13, + 0x25, 0x91, 0x59, 0xCA, 0xC4, 0x76, 0x9C, 0x34, 0xA0, 0x80, 0x23, 0xA3, 0x38, 0x8C, 0x35, 0x05, 0x40, 0x6F, 0xB2, 0x1C, 0x69, 0xEE, 0xC1, 0x2D, 0xAC, 0x95, 0xA3, 0xC9, 0xBA, 0x61, 0x18, 0x52, + 0x37, 0xF0, 0xFF, 0x1E, 0x0E, 0x05, 0xF1, 0xA6, 0xF5, 0xA0, 0xC0, 0x90, 0x90, 0x10, 0x06, 0x65, 0xA1, 0xAD, 0x3A, 0xFB, 0x10, 0x76, 0x84, 0x7B, 0x23, 0x2E, 0xEE, 0xA7, 0x84, 0x09, 0xBD, 0x90, + 0x55, 0xDB, 0x57, 0xC1, 0xB3, 0x1E, 0x28, 0xA0, 0x1D, 0x09, 0x99, 0x90, 0x35, 0xBD, 0xFC, 0x65, 0x7A, 0x61, 0x04, 0x01, 0x03, 0xEC, 0xEB, 0xDC, 0x79, 0x34, 0x09, 0x73, 0x37, 0x34, 0xD9, 0x34, + 0x2C, 0xC5, 0xA0, 0x69, 0xE0, 0x70, 0xC2, 0x42, 0x1D, 0xDE, 0x11, 0xC4, 0x9E, 0x17, 0x2D, 0xBE, 0x7F, 0xEA, 0xF9, 0xDE, 0xDD, 0xFB, 0x3D, 0xA5, 0xDA, 0xA6, 0xB3, 0xDD, 0x13, 0x20, 0x0B, 0x09, + 0x04, 0x2E, 0x14, 0x4E, 0xEA, 0x95, 0x1B, 0x43, 0xDA, 0x48, 0x15, 0x3C, 0x1F, 0x1D, 0x5C, 0x07, 0xFC, 0xF4, 0x73, 0xFA, 0x7F, 0x32, 0x1E, 0x72, 0x53, 0x45, 0x77, 0xC8, 0x95, 0x15, 0x1B, 0x46, + 0xE4, 0x83, 0x31, 0xDD, 0xE6, 0x1D, 0xA4, 0x5F, 0x86, 0x09, 0xAC, 0x59, 0x58, 0x18, 0x14, 0x66, 0x6E, 0x16, 0x58, 0xB4, 0x91, 0x14, 0x52, 0x4B, 0xA3, 0x84, 0x0C, 0x6B, 0xC5, 0x59, 0x65, 0x51, + 0xAE, 0xF4, 0x24, 0x12, 0xC8, 0xAA, 0xCC, 0xDD, 0x8E, 0xF6, 0x9E, 0x46, 0x38, 0x0E, 0x6D, 0xEF, 0x60, 0xFD, 0x91, 0x22, 0x8B, 0x99, 0xCB, 0x51, 0x1D, 0x68, 0xEF, 0x66, 0x31, 0x74, 0x8A, 0x05, + 0x48, 0x08, 0x3A, 0x21, 0x54, 0x45, 0xEC, 0x54, 0x69, 0x34, 0x71, 0xA8, 0x31, 0x04, 0x2C, 0xF4, 0x1D, 0x09, 0xAF, 0x89, 0x81, 0x19, 0xB0, 0xFC, 0x64, 0x6E, 0x48, 0x45, 0x39, 0xC8, 0xC3, 0x2D, + 0x5D, 0xC2, 0x4F, 0x94, 0x39, 0xD3, 0x3E, 0xEE, 0xA0, 0x33, 0xA4, 0x08, 0x15, 0x50, 0xFD, 0xB0, 0xB0, 0x89, 0x23, 0xDB, 0xA5, 0xD4, 0x4A, 0x1A, 0x87, 0x6F, 0xE7, 0xEE, 0x43, 0x20, 0xBF, 0x02, + 0xF9, 0xBE, 0x26, 0xF4, 0x18, 0xF3, 0x09, 0xFA, 0x11, 0xFC, 0xD0, 0xC8, 0x64, 0xA7, 0xAA, 0x34, 0x11, 0x50, 0x83, 0xC1, 0xEA, 0x77, 0x53, 0x45, 0xAC, 0x05, 0x48, 0xC8, 0x77, 0xC6, 0x85, 0xEA, + 0x8C, 0x91, 0xB9, 0x24, 0xAF, 0x4F, 0x60, 0x7E, 0xF3, 0x7A, 0x02, 0x08, 0xE2, 0x13, 0x09, 0xAB, 0x6D, 0x0F, 0x2F, 0x8A, 0x4E, 0xAA, 0x04, 0x51, 0xFF, 0x4A, 0x47, 0xE6, 0xF4, 0x82, 0x95, 0x8D, + 0x81, 0xA1, 0x66, 0xA6, 0xA0, 0x8A, 0x6A, 0x10, 0xFC, 0x8F, 0x9A, 0xDA, 0x42, 0xB6, 0x4A, 0x12, 0xB9, 0x35, 0x7D, 0x59, 0x8A, 0x36, 0x64, 0xE9, 0xDF, 0x13, 0x75, 0x5C, 0x10, 0xFF, 0xD7, 0x17, + 0x7E, 0x59, 0x4D, 0xFC, 0xBC, 0xFB, 0x5D, 0x11, 0xB6, 0xAD, 0xB1, 0x60, 0x74, 0x45, 0x47, 0x9A, 0x5D, 0xB1, 0xAD, 0x8C, 0xA6, 0xD9, 0x15, 0xF8, 0x97, 0x95, 0xD2, 0x40, 0xCB, 0xED, 0xFA, 0xD2, + 0x53, 0x9D, 0x10, 0x51, 0x8E, 0x53, 0xCC, 0x45, 0x0D, 0x6F, 0xC5, 0x38, 0x5A, 0xD6, 0xD7, 0x6B, 0x78, 0x30, 0xF1, 0x38, 0x28, 0x12, 0x06, 0x45, 0xE3, 0xA0, 0xA5, 0xDC, 0xDE, 0xAF, 0x15, 0xF1, + 0x96, 0x8E, 0x64, 0xB3, 0xB1, 0xCE, 0xAF, 0x53, 0x6C, 0xAA, 0x29, 0x53, 0xD1, 0x61, 0xC7, 0x55, 0x28, 0xC3, 0xFA, 0x84, 0x93, 0xE0, 0xC1, 0x77, 0xAE, 0x80, 0x7C, 0xED, 0x37, 0x64, 0x8A, 0x82, + 0xC9, 0xBE, 0x8B, 0xA9, 0x70, 0x29, 0x6D, 0x54, 0x3F, 0x6F, 0xBD, 0x67, 0x24, 0xA9, 0x9A, 0x68, 0xD2, 0xF6, 0x8C, 0x1F, 0xD3, 0x33, 0xF9, 0xDE, 0xF8, 0x52, 0x6D, 0xB7, 0x83, 0x64, 0x55, 0xB3, + 0x13, 0xE6, 0xBC, 0x36, 0x61, 0x78, 0xC9, 0xC5, 0x77, 0x21, 0x60, 0x1E, 0xC0, 0x33, 0x50, 0x54, 0xF0, 0x67, 0xB7, 0x8E, 0x66, 0x3A, 0x05, 0x8D, 0xBD, 0xA1, 0xC1, 0x2D, 0x80, 0xA3, 0x92, 0xF8, + 0x9C, 0x0A, 0xD9, 0xE2, 0xA3, 0xB2, 0xEA, 0x17, 0xE9, 0xC9, 0xA3, 0xB1, 0x4D, 0x17, 0x68, 0x22, 0xEE, 0xAC, 0x5F, 0xB5, 0xFF, 0x7D, 0x4C, 0x87, 0xD7, 0x60, 0x80, 0xD2, 0xD4, 0x2D, 0x9A, 0xA4, + 0xC9, 0x51, 0xF4, 0xCA, 0xF1, 0x1A, 0x24, 0x4E, 0xDA, 0x71, 0x1D, 0x12, 0x0A, 0x2E, 0xA3, 0x21, 0xD1, 0x55, 0x1D, 0x86, 0xCA, 0x92, 0x65, 0xE9, 0xCD, 0x5F, 0xA9, 0x59, 0x1D, 0x88, 0x0E, 0x40, + 0x3B, 0x68, 0x44, 0xF0, 0x51, 0xDC, 0x04, 0x87, 0x99, 0x72, 0xC8, 0x63, 0xB9, 0x7C, 0x72, 0xB4, 0x09, 0xC1, 0x9D, 0x5E, 0xBE, 0xE8, 0xAB, 0x58, 0xC6, 0xE7, 0xB3, 0x93, 0x8A, 0x68, 0xA9, 0xCA, + 0xD7, 0x5D, 0x80, 0xC6, 0xFF, 0xC4, 0xF2, 0x22, 0x54, 0xFF, 0x44, 0x20, 0xC6, 0x06, 0xAD, 0x12, 0x0C, 0xC2, 0x03, 0x46, 0xA7, 0xE7, 0x32, 0x4E, 0x78, 0xC8, 0x62, 0xE0, 0xDE, 0xE1, 0x61, 0xA6, + 0x4F, 0x44, 0x91, 0x7D, 0xB0, 0xC3, 0x8C, 0x1F, 0x79, 0xC9, 0x69, 0x22, 0x0D, 0x20, 0x2F, 0x88, 0x02, 0xD0, 0xF9, 0xD7, 0xAB, 0xFB, 0x2D, 0xE4, 0x34, 0xB1, 0xC5, 0x3D, 0xAB, 0xB5, 0x75, 0x75, + 0xEE, 0xBB, 0xBF, 0x31, 0xCF, 0xB2, 0x92, 0x48, 0x72, 0xFA, 0x01, 0x47, 0x3B, 0x39, 0x76, 0xAE, 0xAD, 0xC9, 0x96, 0x99, 0xB1, 0x38, 0x20, 0xFA, 0x08, 0x68, 0xF2, 0xC9, 0xFD, 0x0D, 0x35, 0x2E, + 0x25, 0x93, 0x27, 0x3C, 0xD6, 0x21, 0xB1, 0x97, 0x4F, 0xFA, 0x61, 0x87, 0xFA, 0x05, 0xC4, 0x11, 0x8D, 0x45, 0x17, 0xC9, 0x34, 0x15, 0x1C, 0x1F, 0xA3, 0x4B, 0xEC, 0x3E, 0xD3, 0x63, 0x95, 0x98, + 0xCB, 0xA2, 0x4E, 0x28, 0x22, 0x9C, 0xE9, 0xFD, 0x3B, 0x1D, 0xB4, 0x96, 0x9C, 0x12, 0xEE, 0x49, 0xE1, 0x8B, 0x36, 0xCE, 0x2B, 0x91, 0x45, 0xAA, 0xC7, 0x54, 0x28, 0xDF, 0xFA, 0x14, 0x53, 0x02, + 0xF4, 0x1D, 0x9E, 0x33, 0x94, 0xF3, 0x8D, 0x3F, 0x3C, 0x03, 0x34, 0xC4, 0x77, 0x4F, 0x1E, 0x94, 0x29, 0x6D, 0xE3, 0x6D, 0xC6, 0xE4, 0x30, 0xE4, 0xC0, 0xA5, 0x37, 0xE6, 0x8B, 0xDD, 0x41, 0xAF, + 0x04, 0x21, 0x19, 0x3B, 0x16, 0xAB, 0x18, 0x91, 0xFA, 0x83, 0x6C, 0xBC, 0x36, 0x7B, 0x40, 0x37, 0x05, 0xAB, 0xA5, 0xD2, 0xF9, 0xF2, 0xA4, 0xC2, 0xF2, 0x75, 0xEC, 0x01, 0x0B, 0x2E, 0xAB, 0x84, + 0x09, 0x5A, 0x56, 0x9D, 0xBA, 0xE4, 0x45, 0x7C, 0xC2, 0xAC, 0x1C, 0xFE, 0xB1, 0xED, 0xA4, 0x3C, 0x3E, 0x28, 0x19, 0x27, 0x3C, 0x48, 0x7A, 0xCB, 0xEB, 0xFA, 0x0A, 0x0E, 0xD1, 0xCC, 0x46, 0x67, + 0xA6, 0xF5, 0x77, 0xF6, 0x2D, 0xFB, 0x1B, 0xC8, 0xFE, 0xAF, 0xD8, 0x6D, 0x90, 0x10, 0x8E, 0x16, 0xB8, 0xB0, 0xE6, 0xC2, 0x67, 0x86, 0x86, 0xC9, 0x28, 0xA6, 0x68, 0xBB, 0x98, 0x57, 0xFF, 0xB2, + 0x8D, 0xE9, 0x05, 0x45, 0xCD, 0x44, 0x37, 0xDD, 0x32, 0xCC, 0xCC, 0xC6, 0xED, 0x58, 0xFB, 0x46, 0xFB, 0xF8, 0x5E, 0x0A, 0xEC, 0x0C, 0x81, 0x4E, 0x53, 0x62, 0x45, 0x25, 0x2B, 0x80, 0x29, 0xF0, + 0xA2, 0xAB, 0x44, 0xB9, 0x02, 0x7A, 0x7E, 0x35, 0xA9, 0x41, 0xFA, 0x11, 0x3C, 0x8D, 0x82, 0x97, 0x4E, 0xA2, 0x2D, 0xF0, 0x2D, 0x84, 0xE5, 0x32, 0x8C, 0xEA, 0x83, 0xD1, 0x2D, 0x39, 0x9C, 0x7F, + 0x02, 0x59, 0x05, 0x5F, 0x4B, 0x3A, 0xD7, 0x07, 0xE7, 0xB3, 0xE5, 0x37, 0xB9, 0x3D, 0xEA, 0x1A, 0x06, 0x6B, 0xDC, 0x77, 0x5F, 0xC7, 0xD1, 0xA6, 0xF0, 0xFE, 0x29, 0xDD, 0xAF, 0xA9, 0xA7, 0xDA, + 0x63, 0x0A, 0x46, 0x7E, 0xF6, 0xCB, 0xF5, 0xCC, 0xDF, 0xFD, 0x79, 0xF1, 0xC8, 0xBB, 0x6B, 0xB3, 0x88, 0x20, 0x35, 0xC7, 0x3C, 0xDF, 0x7E, 0xCF, 0xFB, 0x53, 0xC7, 0x12, 0xA7, 0xC7, 0xEA, 0xA5, + 0x97, 0x65, 0xEF, 0xA9, 0x60, 0xBF, 0x21, 0xE2, 0x5A, 0x67, 0x03, 0xFB, 0x30, 0x4F, 0x07, 0x73, 0x9F, 0xEB, 0xC6, 0x3F, 0x49, 0x6B, 0x13, 0xCC, 0xAA, 0x07, 0x73, 0x38, 0xA0, 0xB9, 0xA9, 0x76, + 0xA9, 0xF0, 0xFC, 0x57, 0x42, 0xD8, 0x5C, 0x4A, 0xF4, 0x01, 0xA4, 0xCE, 0x34, 0x1B, 0x47, 0xBE, 0x25, 0x94, 0xFF, 0x7E, 0x30, 0x19, 0xA0, 0xE0, 0x64, 0x53, 0x5F, 0x9D, 0x93, 0x95, 0xCC, 0x74, + 0xA6, 0xA6, 0xF0, 0x0E, 0x0C, 0x4E, 0x35, 0x30, 0xA7, 0xFE, 0x93, 0x10, 0xCE, 0x30, 0xB6, 0x92, 0x2D, 0x04, 0xFD, 0xE0, 0xAA, 0x74, 0x9C, 0xC3, 0xFD, 0xED, 0xB4, 0xD8, 0x70, 0x8C, 0x1F, 0x69, + 0x68, 0xBB, 0xED, 0xDD, 0xD5, 0x83, 0x3B, 0x29, 0x9D, 0x79, 0xD6, 0x14, 0x28, 0x18, 0x00, 0x99, 0xB0, 0xA9, 0x46, 0xA5, 0xD7, 0x90, 0x85, 0xDF, 0x7F, 0x87, 0x2C, 0xBD, 0xD2, 0x19, 0xE6, 0xB8, + 0xEF, 0x8B, 0x8A, 0xB5, 0xC1, 0xA1, 0x49, 0xE6, 0xE1, 0x5E, 0xF2, 0x82, 0x86, 0x54, 0xFA, 0xBE, 0xC2, 0x49, 0xAF, 0xAA, 0xC4, 0xDC, 0x0B, 0x3B, 0x54, 0x23, 0x34, 0x16, 0x2F, 0xB0, 0x98, 0x00, + 0xB6, 0xC3, 0x6C, 0xC9, 0x0F, 0x2A, 0x10, 0x65, 0x58, 0xBA, 0xE2, 0x19, 0x8F, 0xA7, 0xD1, 0xE2, 0xD7, 0x30, 0xDE, 0x46, 0xE3, 0x55, 0xAE, 0xA9, 0x32, 0x48, 0xE5, 0x3A, 0xB2, 0x1B, 0x51, 0x8E, + 0xC9, 0x9D, 0x5F, 0x3B, 0x02, 0x11, 0x96, 0xA0, 0xF6, 0x14, 0xA4, 0x6B, 0x94, 0x75, 0x62, 0x12, 0x34, 0x73, 0x3A, 0x28, 0xA4, 0x65, 0xCC, 0x5A, 0x7F, 0xD4, 0x32, 0xC3, 0x62, 0x58, 0x12, 0xAA, + 0xBB, 0xB4, 0x2D, 0x2D, 0x9C, 0xBE, 0xF1, 0x6C, 0xBE, 0xD9, 0x36, 0x72, 0x02, 0xB0, 0x28, 0x94, 0xD0, 0x6B, 0xB8, 0x01, 0xBD, 0xA8, 0x47, 0x2B, 0x99, 0x18, 0xB7, 0xD7, 0x24, 0xE3, 0x65, 0x57, + 0xDB, 0xE6, 0xB7, 0x63, 0x3A, 0x5F, 0xD2, 0x2D, 0x0E, 0x33, 0x6E, 0x55, 0x57, 0xAF, 0xC0, 0x18, 0xC8, 0x12, 0xE9, 0xE6, 0xA3, 0x5B, 0xFD, 0x8C, 0x60, 0xAB, 0x38, 0x2E, 0x14, 0xFF, 0x51, 0x14, + 0x2B, 0x2D, 0x2C, 0x75, 0xA7, 0x67, 0xF3, 0x24, 0x13, 0xBA, 0x38, 0x48, 0x75, 0x58, 0xF9, 0x34, 0x5C, 0xBE, 0x6F, 0xD1, 0xD6, 0xB7, 0x8C, 0x2E, 0x62, 0x2F, 0x3B, 0x97, 0x62, 0x30, 0xF9, 0x9D, + 0x6C, 0xBA, 0xF0, 0xBB, 0xD1, 0x49, 0x49, 0x51, 0x0A, 0x52, 0x64, 0x4E, 0xF3, 0xF3, 0x07, 0x88, 0x65, 0x03, 0x7A, 0x1C, 0x10, 0xF4, 0x7B, 0x59, 0x54, 0x66, 0x99, 0xE1, 0xBD, 0x53, 0x9C, 0x7D, + 0xDC, 0xC0, 0x3F, 0x71, 0xA0, 0x15, 0x8E, 0xA9, 0xF0, 0x17, 0x8E, 0x18, 0x7B, 0xB6, 0xD4, 0x94, 0x40, 0xDF, 0x2B, 0x10, 0x63, 0x0F, 0xBE, 0x2F, 0xEB, 0x50, 0x97, 0xE4, 0x7F, 0x28, 0x57, 0x11, + 0xCA, 0x6F, 0x83, 0x5A, 0x10, 0xD3, 0xAA, 0x75, 0xC0, 0x3C, 0x41, 0x84, 0xC0, 0x3E, 0xF3, 0x07, 0x5D, 0x49, 0xDC, 0xB2, 0x17, 0x7A, 0xBD, 0x53, 0xAD, 0x73, 0x99, 0xD2, 0x90, 0xEA, 0x69, 0x1D, + 0x64, 0x73, 0x29, 0x05, 0x63, 0x40, 0xE8, 0xC8, 0x36, 0xE9, 0x75, 0x0F, 0xD8, 0x81, 0xDC, 0xE3, 0x09, 0xD3, 0x09, 0xA9, 0x5B, 0x82, 0x49, 0x2D, 0x4B, 0xDC, 0x15, 0xEC, 0xF8, 0xC7, 0xF5, 0xD3, + 0xB9, 0xDD, 0x27, 0x55, 0x48, 0x51, 0x2D, 0xB5, 0xEF, 0x80, 0xCD, 0x40, 0x9E, 0xD3, 0x2B, 0x51, 0x48, 0xB8, 0x2B, 0xF2, 0x40, 0xA7, 0xDC, 0x72, 0xA1, 0x85, 0x23, 0xD8, 0x08, 0xB7, 0xA4, 0xF9, + 0xE2, 0x54, 0x79, 0x9E, 0x17, 0x27, 0x8F, 0xA8, 0x8D, 0xAE, 0xBC, 0x94, 0x46, 0x32, 0xE8, 0x3F, 0x86, 0x09, 0xD6, 0x81, 0xAB, 0x46, 0x35, 0x13, 0x02, 0x3D, 0x67, 0xCD, 0x51, 0xB1, 0x53, 0xF0, + 0x96, 0x29, 0x12, 0xDD, 0x64, 0xAB, 0x8F, 0x65, 0x29, 0xDC, 0x22, 0xAA, 0x89, 0xE5, 0x72, 0xA7, 0xF8, 0x9C, 0xB9, 0x7A, 0x8F, 0x45, 0x09, 0x31, 0x9D, 0x22, 0x3B, 0xB2, 0x99, 0x74, 0x95, 0x17, + 0x16, 0xFD, 0x31, 0x77, 0x14, 0x0A, 0x31, 0xEA, 0x20, 0x04, 0x8B, 0xAF, 0x0F, 0xCA, 0x23, 0x0C, 0xEF, 0x21, 0x96, 0x7A, 0xBD, 0x83, 0x30, 0x9A, 0x4F, 0xF7, 0xE3, 0x5E, 0x88, 0x78, 0x4D, 0xCA, + 0x77, 0xAC, 0x07, 0x90, 0x20, 0xEC, 0x0C, 0xA6, 0xDD, 0xEF, 0xBC, 0xBB, 0x7E, 0x31, 0x73, 0x29, 0x31, 0x46, 0x65, 0xD7, 0xC5, 0x1F, 0x63, 0x1F, 0x68, 0x1B, 0x60, 0x03, 0x64, 0xE4, 0x75, 0x74, + 0xF2, 0x52, 0xBA, 0xD6, 0x39, 0x6B, 0x3F, 0x5B, 0x17, 0xAD, 0xC2, 0x20, 0x96, 0x6A, 0x93, 0xCE, 0x8F, 0x31, 0x5A, 0x2F, 0x83, 0x06, 0x8D, 0x2E, 0xA0, 0x69, 0x52, 0xE6, 0xEB, 0xD8, 0x02, 0x47, + 0x3A, 0x22, 0x64, 0xEF, 0xA4, 0x05, 0xB3, 0xE4, 0x91, 0xBE, 0x77, 0x6C, 0x50, 0x40, 0x6E, 0x11, 0x50, 0xC5, 0x6B, 0x89, 0x4C, 0xF8, 0x64, 0x54, 0x6B, 0x0C, 0x7A, 0x65, 0xE3, 0xF1, 0xA2, 0xBE, + 0xFE, 0xF2, 0xA9, 0x99, 0x0B, 0xAF, 0xE7, 0x0B, 0x6C, 0xA9, 0xF9, 0x1A, 0x8F, 0x3D, 0xD2, 0x13, 0x07, 0xA3, 0x9A, 0x2A, 0xFB, 0xDF, 0xBD, 0xE9, 0xB7, 0xCA, 0x3D, 0x78, 0x28, 0xB1, 0x3F, 0x49, + 0xDE, 0xCD, 0x72, 0x9C, 0x00, 0x39, 0xE9, 0x4E, 0xBB, 0x7B, 0x4B, 0xDA, 0x09, 0xB3, 0x50, 0x55, 0x29, 0xA1, 0x2C, 0xB1, 0xE2, 0xFD, 0x79, 0xB9, 0xE5, 0x08, 0x7C, 0xD7, 0xC3, 0xBC, 0x05, 0xF7, + 0xCF, 0xFB, 0xBA, 0x93, 0x2A, 0x7B, 0xFF, 0x8E, 0x67, 0x55, 0x5F, 0xEE, 0x03, 0x04, 0xD8, 0x90, 0x31, 0x3F, 0x86, 0xE1, 0x89, 0x25, 0x69, 0xE2, 0xD6, 0xF1, 0x4A, 0x89, 0x93, 0x87, 0x17, 0xAA, + 0xA3, 0xA3, 0x2A, 0xD1, 0x16, 0x71, 0x50, 0x29, 0x9C, 0x21, 0x82, 0x0A, 0xBD, 0x70, 0xFF, 0x90, 0x2B, 0x00, 0x4C, 0x6D, 0xE9, 0x1C, 0x1C, 0x0B, 0x40, 0x70, 0x64, 0x42, 0xAF, 0x53, 0x1E, 0xC4, + 0x90, 0xB0, 0x12, 0x75, 0x0B, 0xCB, 0x48, 0x77, 0x93, 0x5A, 0x7E, 0x54, 0x03, 0x17, 0x02, 0xBB, 0x98, 0x8E, 0xB3, 0xF9, 0x29, 0x14, 0xCD, 0xBD, 0x42, 0x97, 0x9A, 0xD7, 0xD2, 0x7B, 0x22, 0x33, + 0xEC, 0x12, 0x79, 0xD0, 0x54, 0x93, 0xB1, 0x2D, 0x3F, 0x5F, 0xBB, 0x77, 0x57, 0x53, 0x60, 0x21, 0xB5, 0xF4, 0xCD, 0x93, 0x2B, 0x48, 0x0E, 0x40, 0xCB, 0xAE, 0x50, 0xD2, 0x32, 0xE0, 0xA2, 0xEF, + 0xFE, 0x0E, 0x8C, 0xB5, 0x88, 0x08, 0x66, 0x91, 0x99, 0xF0, 0x83, 0x08, 0x72, 0xF3, 0x69, 0x73, 0x86, 0x82, 0xF8, 0x46, 0xF6, 0xDE, 0xAD, 0x09, 0x5B, 0xFF, 0xCD, 0x67, 0x0A, 0x4A, 0x9C, 0xD1, + 0x42, 0x39, 0x6C, 0x58, 0x50, 0x6E, 0xA7, 0xA6, 0x8B, 0x21, 0xAB, 0xDC, 0xC1, 0x9C, 0xCC, 0x06, 0xF6, 0xDA, 0x55, 0xC8, 0x85, 0xA8, 0x55, 0xC4, 0x56, 0x68, 0x0C, 0xD4, 0x47, 0x7B, 0xCA, 0x2B, + 0xBA, 0x91, 0x53, 0xDC, 0xAE, 0xE6, 0x82, 0x65, 0x5B, 0x74, 0xEC, 0xA6, 0xF7, 0xE4, 0x4C, 0x3B, 0xFE, 0x1E, 0x2D, 0x45, 0x74, 0x91, 0xED, 0x1B, 0xC6, 0x4E, 0x1C, 0xF6, 0xCE, 0x18, 0xCF, 0x44, + 0xA0, 0x16, 0x6D, 0x1B, 0x24, 0x44, 0x80, 0x88, 0x2C, 0x1B, 0x35, 0xCE, 0xA7, 0x03, 0x15, 0x8E, 0x18, 0xC7, 0xEC, 0x6E, 0x0C, 0xF8, 0x27, 0xD5, 0x50, 0x4A, 0x45, 0xAE, 0x61, 0x15, 0x23, 0x09, + 0xBC, 0x8A, 0x18, 0xA5, 0x2C, 0x0E, 0x76, 0x99, 0xA8, 0x7C, 0x4E, 0x31, 0xC6, 0x91, 0x1A, 0x83, 0x05, 0x35, 0x15, 0x55, 0xB2, 0x97, 0x1C, 0x94, 0x60, 0x2B, 0x70, 0xE6, 0x70, 0xAA, 0x30, 0xB9, + 0x07, 0x34, 0xEC, 0x1D, 0xAA, 0xD0, 0x3A, 0x30, 0xA9, 0x6F, 0x58, 0x47, 0xC5, 0xC3, 0xF7, 0x97, 0x3C, 0xF4, 0x57, 0x2D, 0x16, 0x6C, 0x51, 0xD1, 0xE9, 0x4A, 0x50, 0xA4, 0xC1, 0xC8, 0x94, 0xA2, + 0x05, 0xF8, 0xEC, 0xB3, 0x4E, 0x80, 0xF8, 0x4C, 0xA8, 0xDC, 0x31, 0xA4, 0x29, 0xD5, 0x60, 0x05, 0x96, 0x17, 0x9D, 0x10, 0x93, 0xE2, 0xA3, 0x89, 0xCC, 0xFE, 0x9C, 0x04, 0x02, 0xEE, 0x49, 0x55, + 0x17, 0x10, 0xFF, 0xC2, 0x5B, 0xDB, 0xE4, 0x78, 0xF3, 0x9F, 0x20, 0x63, 0xF3, 0x1F, 0x75, 0xD7, 0x43, 0x2E, 0xCA, 0x1C, 0x59, 0xEB, 0xD8, 0xF4, 0x6D, 0x86, 0xA0, 0x92, 0xDB, 0x12, 0xF8, 0x10, + 0xFA, 0x91, 0x1C, 0x20, 0xD4, 0xCC, 0x1E, 0x42, 0x5C, 0x54, 0x3D, 0xC6, 0x45, 0x77, 0xE4, 0x4D, 0x84, 0xF4, 0x22, 0xD9, 0x66, 0x1E, 0x3D, 0x35, 0x92, 0x13, 0x50, 0xD6, 0xF7, 0x09, 0x9C, 0x54, + 0x25, 0xE5, 0x09, 0xE1, 0x45, 0x8A, 0x05, 0x00, 0xAE, 0x5E, 0xB4, 0xCC, 0x6B, 0xB5, 0x06, 0x26, 0xD0, 0x13, 0x0F, 0x09, 0x36, 0x17, 0x17, 0xA9, 0x59, 0x19, 0xAE, 0xD3, 0x55, 0x92, 0xFA, 0x4A, + 0xBE, 0x7B, 0x2B, 0xD4, 0xF9, 0x99, 0x42, 0x21, 0x51, 0xE6, 0x3D, 0x4E, 0xD0, 0x0C, 0xC7, 0x51, 0xA5, 0x86, 0x79, 0x77, 0xF1, 0x5E, 0x48, 0x2E, 0xFA, 0x01, 0xE5, 0xCC, 0xC4, 0x40, 0x64, 0xF5, + 0xB9, 0xFF, 0xE2, 0x9A, 0xFF, 0xE6, 0x26, 0xC4, 0xD5, 0x17, 0x0A, 0xDA, 0x1D, 0xF0, 0x27, 0xAB, 0x41, 0x79, 0x60, 0x8C, 0x40, 0x93, 0xCC, 0xE2, 0xC4, 0x09, 0x30, 0x8C, 0xD8, 0x98, 0x37, 0x1A, + 0x49, 0xFB, 0xEA, 0x2A, 0x2F, 0x2B, 0xA1, 0x3B, 0xDE, 0xBA, 0xC1, 0xF4, 0x15, 0x9F, 0x4B, 0x03, 0x68, 0xFB, 0x21, 0xD7, 0x0A, 0x9D, 0x79, 0x31, 0xD7, 0xEF, 0xF9, 0x34, 0xE6, 0xC5, 0x44, 0xE1, + 0x3B, 0x7B, 0x73, 0xD4, 0x65, 0x57, 0x6C, 0x6E, 0x81, 0xFD, 0x6D, 0x5F, 0xD9, 0x43, 0x93, 0xE8, 0x02, 0x42, 0xF9, 0x42, 0x0A, 0xCC, 0x0E, 0xD3, 0x53, 0xEF, 0x18, 0xCA, 0x07, 0x0F, 0x5E, 0x9A, + 0x28, 0x5A, 0xC4, 0xBC, 0xBA, 0xB1, 0x9A, 0x38, 0x35, 0x6F, 0x55, 0x7B, 0x07, 0x0E, 0x17, 0xAE, 0x5C, 0xF1, 0xF1, 0xBE, 0xD4, 0x26, 0x01, 0xE8, 0x9C, 0x8C, 0x4C, 0xA0, 0x82, 0x07, 0x85, 0x03, + 0x82, 0x07, 0x81, 0x00, 0xD9, 0xFD, 0xE3, 0xA4, 0x96, 0xF7, 0x58, 0x19, 0xF0, 0xA2, 0x0D, 0x04, 0x41, 0xDC, 0x78, 0x30, 0xB4, 0xAA, 0x1C, 0xB8, 0xEC, 0xFC, 0x91, 0xBA, 0x0E, 0xEC, 0x3A, 0xFB, + 0x67, 0x44, 0xE4, 0x77, 0xB4, 0xE6, 0xEC, 0x3F, 0xDA, 0xE7, 0x50, 0x48, 0xFF, 0xEB, 0xAA, 0xBE, 0xA8, 0xE8, 0x22, 0x11, 0x7D, 0x57, 0x87, 0xF7, 0x90, 0x70, 0xEA, 0x88, 0x28, 0x7C, 0xE3, 0xCD, + 0x50, 0x11, 0xFD, 0x8D, 0x93, 0xAB, 0x7E, 0x8B, 0x51, 0xF2, 0x61, 0x16, 0xBF, 0x9B, 0x6D, 0x21, 0xC0, 0x3F, 0x88, 0xBF, 0xEC, 0x48, 0x88, 0x76, 0xF4, 0xD0, 0x75, 0xA1, 0x42, 0xD4, 0xE7, 0x84, + 0xD7, 0x34, 0x40, 0x75, 0x11, 0xF9, 0x92, 0x06, 0x93, 0x53, 0xF1, 0xDB, 0x67, 0xAC, 0xF7, 0x30, 0x34, 0xA4, 0x68, 0xA1, 0x18, 0x58, 0x80, 0x62, 0x11, 0x1D, 0x32, 0x0E, 0x00, 0xBC, 0xFF, 0x6D, + 0xC6, 0x35, 0x73, 0xFC, 0xED, 0x1E, 0x96, 0xAA, 0xEB, 0xA6, 0x45, 0x2E, 0x3C, 0x7A, 0xCD, 0x19, 0x18, 0x1F, 0x9B, 0x81, 0x4B, 0xA1, 0x9D, 0x39, 0xB4, 0xBA, 0xB5, 0x49, 0x6D, 0xC0, 0x55, 0x42, + 0x6E, 0x7E, 0xA4, 0x61, 0xAF, 0x55, 0xD5, 0xB9, 0xFE, 0x97, 0xF9, 0xDF, 0x7E, 0x25, 0x32, 0x03, 0xC1, 0xF9, 0xE1, 0x52, 0xE9, 0x6D, 0x75, 0xF9, 0xD9, 0xA8, 0x4F, 0x5C, 0x26, 0x3E, 0xC8, 0xC2, + 0x50, 0x44, 0x0A, 0xDC, 0x98, 0x6F, 0x4E, 0x36, 0x41, 0x4C, 0x70, 0x3B, 0x3E, 0x05, 0x42, 0x6B, 0x28, 0xB7, 0x06, 0x59, 0x50, 0xDA, 0x6D, 0x0E, 0x0B, 0x2C, 0x60, 0xAC, 0x36, 0x72, 0xDB, 0x6F, + 0x3C, 0x78, 0x44, 0x7D, 0xB7, 0xC2, 0x09, 0x15, 0x77, 0x0E, 0xA6, 0xFC, 0xE8, 0x1D, 0xAB, 0x53, 0x39, 0xC1, 0xD5, 0xAF, 0x82, 0xA5, 0xD3, 0x32, 0x40, 0x99, 0xDF, 0x56, 0x51, 0x6A, 0x07, 0xDB, + 0x7C, 0x0F, 0xC6, 0x43, 0x83, 0x80, 0x5C, 0x65, 0xF2, 0xB0, 0x2F, 0xBC, 0xFC, 0xE6, 0x3E, 0x93, 0xC4, 0xBF, 0x09, 0x40, 0x9F, 0x9F, 0x0F, 0x77, 0xE7, 0x3D, 0xA3, 0xB0, 0x01, 0x9F, 0x20, 0x57, + 0xE4, 0xCD, 0x7C, 0xFF, 0x0E, 0x57, 0x45, 0xEF, 0x18, 0xC3, 0xFD, 0x76, 0x6E, 0x01, 0x74, 0x7A, 0x64, 0xD4, 0x15, 0xFC, 0x97, 0x89, 0xAB, 0xFA, 0x62, 0x28, 0x4E, 0x11, 0xC7, 0xFF, 0x05, 0xD0, + 0x54, 0x8D, 0x97, 0x3F, 0x67, 0x95, 0x59, 0xA6, 0xA3, 0xAA, 0xD7, 0x7E, 0xD5, 0x13, 0x2D, 0x01, 0x50, 0xC0, 0x14, 0xC3, 0xEC, 0x3A, 0x39, 0x5F, 0x01, 0x7E, 0x7A, 0xCF, 0xE3, 0xEA, 0xBF, 0xCA, + 0x44, 0x91, 0x0C, 0xA0, 0x6F, 0xF3, 0x35, 0x42, 0xEC, 0xCE, 0x62, 0x41, 0x97, 0x47, 0x42, 0x35, 0x7D, 0x37, 0xF5, 0xC2, 0x84, 0xBF, 0x0F, 0xE1, 0xA7, 0x4B, 0x50, 0xC0, 0x73, 0x55, 0x13, 0x72, + 0x13, 0x3A, 0xF2, 0xDD, 0x41, 0xE2, 0x1B, 0xAF, 0xC9, 0xC5, 0x90, 0xEE, 0x6E, 0xBC, 0x4A, 0xCE, 0x73, 0x1E, 0xF5, 0x66, 0x15, 0x6C, 0xA0, 0x37, 0x55, 0xDC, 0x49, 0x3C, 0x13, 0x70, 0x28, 0xAF, + 0x3B, 0x3D, 0xE5, 0xB0, 0x0B, 0xD6, 0xCB, 0x3D, 0x9A, 0x87, 0xD0, 0x15, 0x1F, 0x88, 0x7C, 0x67, 0x68, 0xBC, 0x6C, 0xA0, 0x2A, 0x94, 0xFB, 0x20, 0x86, 0x55, 0x1A, 0x0F, 0x89, 0xBA, 0x26, 0x15, + 0x4E, 0x9D, 0x45, 0x06, 0xAD, 0x9F, 0xAF, 0x39, 0xF5, 0x72, 0x3E, 0x23, 0x4E, 0x06, 0xCF, 0xDE, 0xD6, 0x9D, 0x4E, 0xE4, 0x14, 0x6B, 0x73, 0xE5, 0xDC, 0x1E, 0x41, 0x52, 0xA2, 0xA3, 0x15, 0x9D, + 0x73, 0xDB, 0xC8, 0x33, 0xD3, 0xD4, 0x17, 0xCD, 0x5C, 0xF7, 0xFB, 0x3D, 0xC7, 0x74, 0x5C, 0xEE, 0xD4, 0xDC, 0x0F, 0x5B, 0x1C, 0x6D, 0x6B, 0x69, 0xC1, 0x76, 0x41, 0x57, 0xEA, 0x43, 0xDF, 0x9D, + 0xBB, 0x44, 0x2E, 0xFA, 0x39, 0xD1, 0xD0, 0x16, 0x2E, 0x87, 0xC2, 0xD3, 0x0C, 0x50, 0x12, 0xFD, 0x16, 0xD8, 0x69, 0xC8, 0xA1, 0xFC, 0xBB, 0x45, 0xED, 0xCC, 0x8E, 0x18, 0x13, 0xB2, 0xB1, 0x90, + 0xA9, 0x61, 0xF9, 0xFC, 0x86, 0x59, 0x1D, 0x3A, 0xBC, 0x53, 0x88, 0xAF, 0x67, 0x8F, 0xF0, 0x3D, 0xA7, 0x8B, 0x7C, 0xC0, 0xF6, 0x18, 0x57, 0x21, 0xC0, 0xDF, 0x33, 0xCC, 0x90, 0x64, 0x35, 0x22, + 0x5D, 0xF2, 0x61, 0x10, 0x02, 0xDF, 0x12, 0x0E, 0x83, 0x56, 0x65, 0x32, 0x29, 0x2D, 0xEA, 0x3D, 0x8A, 0xCD, 0x10, 0x9A, 0x0D, 0xFF, 0xAB, 0x3B, 0x0B, 0x43, 0x01, 0x27, 0x96, 0xDB, 0x5B, 0x50, + 0x68, 0x3F, 0xB4, 0xC2, 0xD2, 0x50, 0xDA, 0xB7, 0x6A, 0xAE, 0x35, 0xA4, 0x8E, 0x8C, 0x8D, 0x4A, 0x5C, 0xC1, 0x54, 0x75, 0x97, 0x45, 0xF0, 0xA1, 0x23, 0x0F, 0x6C, 0xA9, 0xDD, 0x9C, 0x99, 0xE2, + 0xF8, 0x0E, 0xDC, 0x83, 0x30, 0x4C, 0xE0, 0x1E, 0x98, 0xF6, 0xC9, 0x48, 0x95, 0x29, 0xA8, 0x22, 0xF9, 0x00, 0x33, 0xC2, 0x28, 0x31, 0x5E, 0xB2, 0xFC, 0xC8, 0xDB, 0xA3, 0x82, 0xED, 0x43, 0x01, + 0xE0, 0x76, 0x07, 0xA5, 0xB0, 0x76, 0xC7, 0x25, 0xF1, 0x24, 0x99, 0x4F, 0x18, 0xA9, 0x97, 0xD2, 0xC5, 0xBB, 0xF9, 0xA3, 0x24, 0x60, 0x52, 0x65, 0x10, 0x8A, 0xCB, 0xF4, 0x61, 0x0F, 0xA1, 0xC3, + 0x37, 0x44, 0x08, 0x85, 0x0A, 0x08, 0x64, 0xE2, 0xB6, 0x10, 0x17, 0xEB, 0xEC, 0x1F, 0xBA, 0xB8, 0x9D, 0xE3, 0xAB, 0x1B, 0x93, 0xCE, 0x49, 0x18, 0xB9, 0xE2, 0xC9, 0xE3, 0xFE, 0x45, 0x67, 0x58, + 0x06, 0x2A, 0x9F, 0x88, 0x2B, 0x28, 0x33, 0x18, 0x27, 0x1F, 0x4B, 0x95, 0x52, 0xFC, 0xF3, 0x26, 0x24, 0xA9, 0xFD, 0xAA, 0x44, 0xC6, 0x5C, 0x60, 0xE2, 0xB3, 0x64, 0x8B, 0xEF, 0x1F, 0x17, 0xD0, + 0xB7, 0xC7, 0x48, 0x69, 0xEE, 0x0B, 0x53, 0xC4, 0xA6, 0x2A, 0x24, 0x84, 0x5D, 0xCE, 0xA5, 0xBC, 0xBF, 0x93, 0xB9, 0x2E, 0x4C, 0x26, 0x64, 0x85, 0x84, 0xE3, 0x34, 0x79, 0x28, 0x2E, 0x6C, 0x8B, + 0x1D, 0x8F, 0xE2, 0x11, 0x81, 0xBD, 0x9C, 0xF7, 0x5F, 0x8A, 0x96, 0x17, 0x24, 0xD4, 0xC4, 0x30, 0x97, 0x79, 0xF1, 0xF1, 0xB7, 0x75, 0xD2, 0x54, 0xF7, 0x0B, 0xD1, 0x76, 0x9C, 0xC7, 0xC0, 0xED, + 0xD2, 0xA9, 0x5F, 0xE5, 0xC9, 0xD8, 0x4B, 0x16, 0xF7, 0xC5, 0x4D, 0x85, 0xCC, 0xE4, 0xC8, 0xA1, 0x82, 0x81, 0x08, 0x09, 0xED, 0x81, 0xE9, 0x7D, 0x07, 0x48, 0x84, 0xEE, 0xDF, 0x40, 0x1C, 0xCA, + 0xCD, 0xAE, 0xAD, 0x82, 0xC1, 0x4D, 0x06, 0xB6, 0x8A, 0xEA, 0x6C, 0xE1, 0x4B, 0x86, 0x1B, 0x0C, 0xFD, 0x16, 0x09, 0x0C, 0xBB, 0xF4, 0x69, 0xC5, 0xE0, 0x84, 0x31, 0x4C, 0x0D, 0x8D, 0x39, 0x60, + 0xEA, 0x06, 0xA3, 0x42, 0x6D, 0x8B, 0x3F, 0xE7, 0x62, 0xE0, 0x0D, 0x09, 0xBD, 0xA3, 0x74, 0xF3, 0xAE, 0x2C, 0xBE, 0xDE, 0x28, 0x38, 0xFF, 0x89, 0xD8, 0x1D, 0xEB, 0x30, 0x13, 0x09, 0x0E, 0x44, + 0x19, 0x9A, 0xED, 0x60, 0x49, 0x63, 0xEA, 0xF9, 0x19, 0x91, 0x4C, 0xE0, 0x4F, 0x20, 0x7A, 0xC8, 0x2C, 0xD4, 0x35, 0x1F, 0xEF, 0x7B, 0x2D, 0x94, 0x39, 0x30, 0x66, 0xFE, 0x4D, 0x44, 0xE3, 0xCC, + 0x59, 0x52, 0xE7, 0x5E, 0xB6, 0xF3, 0x71, 0x40, 0x58, 0x91, 0x5D, 0xE0, 0xEE, 0x18, 0x4D, 0x8C, 0x55, 0x30, 0x0F, 0x57, 0x6A, 0x8B, 0x82, 0xA8, 0x63, 0xE8, 0x1A, 0xF3, 0x34, 0x17, 0xBD, 0x4C, + 0xFC, 0x94, 0xE7, 0xA6, 0x12, 0x63, 0xB3, 0x9F, 0x01, 0xF6, 0xE2, 0xE7, 0x07, 0x48, 0xB6, 0xE5, 0xE5, 0x9C, 0xF6, 0xCA, 0x01, 0xB0, 0x02, 0x8C, 0x93, 0xBB, 0xBC, 0xEB, 0xC5, 0x48, 0xF9, 0x87, + 0xF1, 0x07, 0x55, 0xBF, 0x33, 0xCA, 0x58, 0x5C, 0xB4, 0x1C, 0xF5, 0x78, 0xDF, 0x5F, 0xFE, 0x37, 0x92, 0x4E, 0x3C, 0x2C, 0x07, 0x2E, 0xD1, 0xDA, 0xC9, 0x16, 0x21, 0x76, 0x97, 0x29, 0x71, 0xE7, + 0x9B, 0x62, 0xFB, 0x20, 0x8F, 0x1A, 0x73, 0xBF, 0x03, 0x61, 0xE2, 0x99, 0x3D, 0xCC, 0xCD, 0x31, 0x10, 0xC3, 0x4D, 0x83, 0x9D, 0x18, 0xDD, 0x43, 0xA5, 0xE8, 0xF0, 0xD9, 0x41, 0xE9, 0x9A, 0xDC, + 0xF4, 0x41, 0x40, 0x5F, 0x32, 0x10, 0x76, 0x71, 0xB2, 0xD8, 0xB2, 0x24, 0x4F, 0x7B, 0xA9, 0x2D, 0xCE, 0xD5, 0x87, 0xA2, 0x10, 0xFE, 0x8F, 0xF4, 0x3C, 0x61, 0x6A, 0xCB, 0x5E, 0x76, 0x6E, 0x6A, + 0xF2, 0xCE, 0xB0, 0x35, 0x99, 0xBA, 0x3D, 0xE3, 0x76, 0xEB, 0x57, 0x35, 0xEF, 0x16, 0x14, 0x39, 0x53, 0xD1, 0xFD, 0xDB, 0x7E, 0x9F, 0x28, 0x74, 0xB0, 0xD6, 0x08, 0x3D, 0xD7, 0xEC, 0x43, 0x86, + 0xAE, 0x00, 0x3F, 0x51, 0xCC, 0xF2, 0xD2, 0x1E, 0xF6, 0x05, 0x91, 0x63, 0xC5, 0x15, 0x21, 0x74, 0x42, 0x3F, 0x57, 0x11, 0x9D, 0x0F, 0xCE, 0x62, 0x7D, 0x76, 0x3D, 0x81, 0xC1, 0x0A, 0xA1, 0x32, + 0x9F, 0x74, 0xC8, 0xD4, 0x45, 0x43, 0x7B, 0xA6, 0x71, 0x8A, 0x33, 0xDB, 0x6E, 0x79, 0x37, 0x51, 0x72, 0xB2, 0xAE, 0x35, 0x91, 0x82, 0x19, 0x78, 0xD5, 0x20, 0x82, 0x4E, 0x2D, 0x2F, 0xF8, 0x98, + 0xB7, 0xF4, 0xC8, 0x67, 0xFF, 0x46, 0x27, 0x22, 0xBC, 0x07, 0xEA, 0xDA, 0xD3, 0x89, 0xA9, 0x10, 0xB6, 0xF6, 0x54, 0x29, 0xDA, 0x12, 0x97, 0x35, 0xFE, 0x04, 0x9E, 0x3E, 0xCB, 0x38, 0x89, 0xF6, + 0x04, 0x7C, 0xF2, 0xBD, 0x2A, 0x88, 0xD5, 0x0A, 0x65, 0x1B, 0x32, 0x35, 0xD2, 0x48, 0x0E, 0x1D, 0xA5, 0xA3, 0x52, 0x47, 0xFA, 0x76, 0xC8, 0x31, 0x73, 0x63, 0x99, 0xD3, 0x7E, 0x8D, 0x03, 0x3C, + 0x1D, 0x05, 0x1C, 0x9B, 0x6A, 0x99, 0xAB, 0x80, 0xB1, 0x31, 0x3F, 0xA2, 0x4C, 0x5C, 0x59, 0x76, 0x6E, 0x6C, 0x51, 0xA3, 0x8F, 0xE9, 0xF1, 0x18, 0x6A, 0x76, 0x7E, 0xEB, 0xD0, 0xD8, 0x80, 0x01, + 0xAE, 0x02, 0x46, 0xCD, 0x4E, 0xBE, 0x2C, 0x97, 0x9D, 0xE8, 0x2C, 0x30, 0xBB, 0xDB, 0x98, 0xB4, 0x74, 0x4F, 0x11, 0xF9, 0xE6, 0x39, 0xED, 0xDD, 0x8C, 0x19, 0x4D, 0x79, 0x11, 0x20, 0x1A, 0x8F, + 0xA7, 0x45, 0x99, 0x1B, 0x4D, 0x8A, 0x57, 0x09, 0xB6, 0x2A, 0x21, 0xB6, 0x3B, 0x97, 0x62, 0x91, 0x3D, 0x36, 0xCE, 0x99, 0x5C, 0x2D, 0x6B, 0x79, 0x15, 0x1E, 0x8D, 0x83, 0x83, 0x8C, 0xD1, 0xF3, + 0x88, 0x40, 0xA9, 0x41, 0x72, 0x55, 0xDD, 0x16, 0x6B, 0x7A, 0x35, 0x84, 0x49, 0x90, 0x03, 0xFB, 0x62, 0x56, 0x11, 0x40, 0x4C, 0x95, 0xB9, 0x60, 0xDF, 0x0D, 0xB1, 0xBC, 0xF1, 0x57, 0x4B, 0x09, + 0x65, 0xDB, 0xD8, 0x34, 0xEE, 0x14, 0x81, 0x17, 0xD5, 0xE0, 0x5A, 0x7C, 0xC7, 0xCC, 0x1A, 0x86, 0x56, 0x18, 0xA2, 0xBE, 0x48, 0x54, 0xDB, 0x89, 0x35, 0xCD, 0xA1, 0xE6, 0x8B, 0xD8, 0xD0, 0x9E, + 0x72, 0xF0, 0xAC, 0x90, 0x53, 0xC8, 0x82, 0xC4, 0xAB, 0xA4, 0x00, 0x4A, 0x61, 0x4D, 0x10, 0x50, 0x53, 0x00, 0xB6, 0x17, 0x6C, 0xA1, 0xF3, 0x24, 0xE2, 0x2E, 0x78, 0x24, 0x29, 0x9F, 0x9C, 0x40, + 0x75, 0x5B, 0x71, 0xD8, 0x2B, 0x67, 0x95, 0x47, 0xF0, 0x6A, 0xD4, 0x8B, 0xE6, 0x6D, 0x68, 0x07, 0x2C, 0x93, 0x90, 0x23, 0x3C, 0x93, 0x3F, 0x80, 0xA1, 0x4F, 0x8D, 0x4A, 0x6B, 0x0B, 0x4E, 0x19, + 0x70, 0xE1, 0xAC, 0xC1, 0xBE, 0xA7, 0xF5, 0xD3, 0xBE, 0x22, 0x44, 0x48, 0xF8, 0x57, 0xBA, 0xB6, 0x8A, 0xEF, 0xA6, 0xD8, 0xCB, 0x81, 0x9B, 0x64, 0x29, 0x4A, 0x12, 0x99, 0x79, 0x16, 0xCD, 0xBF, + 0x56, 0xE9, 0xA8, 0xD0, 0x02, 0xDD, 0x06, 0x5F, 0x12, 0xC6, 0x18, 0x23, 0xF4, 0xFC, 0x21, 0x45, 0x08, 0x23, 0x2E, 0x43, 0x1F, 0x0B, 0x68, 0x98, 0x47, 0x5B, 0xB5, 0xDD, 0x0D, 0x7D, 0x52, 0x8E, + 0x84, 0x0C, 0x22, 0x80, 0x9A, 0xF7, 0xE1, 0x53, 0x63, 0x72, 0x4A, 0x61, 0x3A, 0xCC, 0xFB, 0xE2, 0xB3, 0x74, 0x38, 0xC1, 0x59, 0xCE, 0x14, 0xCB, 0x0C, 0x98, 0xBF, 0xD4, 0x99, 0xC0, 0x8D, 0xAC, + 0x0C, 0xF4, 0x5D, 0x82, 0x1C, 0xC2, 0xFA, 0x47, 0x31, 0x9B, 0x6F, 0xB4, 0xCE, 0xD7, 0xE5, 0x98, 0x5E, 0xC8, 0x27, 0x4D, 0xE0, 0x90, 0x71, 0xD3, 0xC1, 0x0D, 0xA5, 0xBF, 0x9E, 0x52, 0x2B, 0x01, + 0xCE, 0x91, 0xD6, 0x6B, 0x91, 0x79, 0x5D, 0x3D, 0x22, 0xC0, 0x04, 0x83, 0x45, 0x42, 0x75, 0xDD, 0x2B, 0xBD, 0xD7, 0xC2, 0xDC, 0xC4, 0xA1, 0x67, 0xE5, 0xD7, 0xFC, 0xDB, 0xB9, 0xF6, 0x20, 0x8C, + 0xD4, 0xC9, 0xA4, 0x85, 0xFA, 0xAE, 0xB8, 0x09, 0xA7, 0x71, 0x1D, 0xAC, 0x28, 0x65, 0xCE, 0xD4, 0x30, 0x64, 0x74, 0xB2, 0x2B, 0x44, 0x48, 0xF8, 0x5D, 0xF3, 0x34, 0x17, 0xF3, 0xFA, 0xCE, 0x1C, + 0x05, 0xD4, 0x27, 0x03, 0xED, 0x31, 0x30, 0x42, 0xA0, 0x5D, 0xE0, 0x36, 0x27, 0x40, 0x13, 0x01, 0x88, 0xEC, 0xB4, 0x45, 0xBB, 0x25, 0x5D, 0xC7, 0x6E, 0xE8, 0x44, 0x3F, 0x73, 0x31, 0x17, 0xF8, + 0x35, 0x1F, 0x17, 0x60, 0x31, 0x75, 0x55, 0x4F, 0xEB, 0x00, 0xB7, 0xFF, 0x54, 0xD8, 0x07, 0x86, 0xF3, 0x05, 0xCD, 0xE1, 0x8C, 0xD5, 0xEC, 0x56, 0xEC, 0x09, 0x62, 0xA3, 0xE0, 0x44, 0x82, 0xDC, + 0xE3, 0x62, 0x2D, 0x04, 0x0D, 0x24, 0xC4, 0x0F, 0x2E, 0x8A, 0x14, 0xA4, 0x47, 0x65, 0x9D, 0x6C, 0x56, 0x1F, 0x2F, 0xFE, 0xE6, 0x8F, 0x8D, 0x3D, 0xE5, 0x11, 0xB2, 0x3E, 0x8B, 0x17, 0x2A, 0x01, + 0xA3, 0xED, 0xA4, 0xD3, 0x78, 0x0E, 0x74, 0xC6, 0x77, 0x24, 0x43, 0x30, 0xE9, 0xAE, 0xFF, 0x01, 0x9F, 0xE0, 0x7B, 0xE3, 0xD3, 0x3F, 0x32, 0x2F, 0x9C, 0xE2, 0x21, 0x4B, 0x9D, 0x9C, 0xFF, 0x99, + 0xD0, 0x5A, 0x59, 0xE4, 0x75, 0x51, 0x43, 0x2A, 0xE7, 0x6F, 0x4C, 0xD4, 0xF8, 0xDD, 0x51, 0x52, 0x0F, 0xFE, 0x81, 0x1B, 0x4B, 0x93, 0xCD, 0x62, 0x19, 0xC8, 0x1B, 0x63, 0xB1, 0xD6, 0x27, 0x78, + 0x5C, 0x2A, 0x0F, 0xC2, 0x2E, 0x3A, 0xEA, 0x86, 0xCE, 0xEE, 0x1F, 0x7F, 0xBC, 0x4E, 0xFC, 0xB4, 0x6D, 0xDF, 0xBC, 0xD8, 0x8A, 0x02, 0xF3, 0xB4, 0xE6, 0x7C, 0x5F, 0xF2, 0xE8, 0xDC, 0x68, 0xBF, + 0x16, 0xC7, 0x46, 0x99, 0xBB, 0xB6, 0x28, 0x90, 0x2F, 0x72, 0xC3, 0xDE, 0xBC, 0x8B, 0xF5, 0xDF, 0x70, 0x6D, 0x47, 0xA6, 0x05, 0xA1, 0x07, 0xDA, 0xA0, 0x01, 0x41, 0x39, 0xCE, 0x40, 0xF0, 0xD4, + 0x6D, 0x8D, 0x6D, 0xC7, + }, + .spki_len = 1990, + .spki = { + 0x30, 0x82, 0x07, 0xC2, 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0B, 0x07, 0x06, 0x05, 0x05, 0x00, 0x03, 0x82, 0x07, 0xAD, 0x00, 0x30, 0x82, 0x07, 0xA8, 0x03, 0x21, + 0x00, 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, 0x38, 0xD5, 0x06, 0xD8, 0x5B, + 0xEF, 0x03, 0x82, 0x07, 0x81, 0x00, 0xD9, 0xFD, 0xE3, 0xA4, 0x96, 0xF7, 0x58, 0x19, 0xF0, 0xA2, 0x0D, 0x04, 0x41, 0xDC, 0x78, 0x30, 0xB4, 0xAA, 0x1C, 0xB8, 0xEC, 0xFC, 0x91, 0xBA, 0x0E, 0xEC, + 0x3A, 0xFB, 0x67, 0x44, 0xE4, 0x77, 0xB4, 0xE6, 0xEC, 0x3F, 0xDA, 0xE7, 0x50, 0x48, 0xFF, 0xEB, 0xAA, 0xBE, 0xA8, 0xE8, 0x22, 0x11, 0x7D, 0x57, 0x87, 0xF7, 0x90, 0x70, 0xEA, 0x88, 0x28, 0x7C, + 0xE3, 0xCD, 0x50, 0x11, 0xFD, 0x8D, 0x93, 0xAB, 0x7E, 0x8B, 0x51, 0xF2, 0x61, 0x16, 0xBF, 0x9B, 0x6D, 0x21, 0xC0, 0x3F, 0x88, 0xBF, 0xEC, 0x48, 0x88, 0x76, 0xF4, 0xD0, 0x75, 0xA1, 0x42, 0xD4, + 0xE7, 0x84, 0xD7, 0x34, 0x40, 0x75, 0x11, 0xF9, 0x92, 0x06, 0x93, 0x53, 0xF1, 0xDB, 0x67, 0xAC, 0xF7, 0x30, 0x34, 0xA4, 0x68, 0xA1, 0x18, 0x58, 0x80, 0x62, 0x11, 0x1D, 0x32, 0x0E, 0x00, 0xBC, + 0xFF, 0x6D, 0xC6, 0x35, 0x73, 0xFC, 0xED, 0x1E, 0x96, 0xAA, 0xEB, 0xA6, 0x45, 0x2E, 0x3C, 0x7A, 0xCD, 0x19, 0x18, 0x1F, 0x9B, 0x81, 0x4B, 0xA1, 0x9D, 0x39, 0xB4, 0xBA, 0xB5, 0x49, 0x6D, 0xC0, + 0x55, 0x42, 0x6E, 0x7E, 0xA4, 0x61, 0xAF, 0x55, 0xD5, 0xB9, 0xFE, 0x97, 0xF9, 0xDF, 0x7E, 0x25, 0x32, 0x03, 0xC1, 0xF9, 0xE1, 0x52, 0xE9, 0x6D, 0x75, 0xF9, 0xD9, 0xA8, 0x4F, 0x5C, 0x26, 0x3E, + 0xC8, 0xC2, 0x50, 0x44, 0x0A, 0xDC, 0x98, 0x6F, 0x4E, 0x36, 0x41, 0x4C, 0x70, 0x3B, 0x3E, 0x05, 0x42, 0x6B, 0x28, 0xB7, 0x06, 0x59, 0x50, 0xDA, 0x6D, 0x0E, 0x0B, 0x2C, 0x60, 0xAC, 0x36, 0x72, + 0xDB, 0x6F, 0x3C, 0x78, 0x44, 0x7D, 0xB7, 0xC2, 0x09, 0x15, 0x77, 0x0E, 0xA6, 0xFC, 0xE8, 0x1D, 0xAB, 0x53, 0x39, 0xC1, 0xD5, 0xAF, 0x82, 0xA5, 0xD3, 0x32, 0x40, 0x99, 0xDF, 0x56, 0x51, 0x6A, + 0x07, 0xDB, 0x7C, 0x0F, 0xC6, 0x43, 0x83, 0x80, 0x5C, 0x65, 0xF2, 0xB0, 0x2F, 0xBC, 0xFC, 0xE6, 0x3E, 0x93, 0xC4, 0xBF, 0x09, 0x40, 0x9F, 0x9F, 0x0F, 0x77, 0xE7, 0x3D, 0xA3, 0xB0, 0x01, 0x9F, + 0x20, 0x57, 0xE4, 0xCD, 0x7C, 0xFF, 0x0E, 0x57, 0x45, 0xEF, 0x18, 0xC3, 0xFD, 0x76, 0x6E, 0x01, 0x74, 0x7A, 0x64, 0xD4, 0x15, 0xFC, 0x97, 0x89, 0xAB, 0xFA, 0x62, 0x28, 0x4E, 0x11, 0xC7, 0xFF, + 0x05, 0xD0, 0x54, 0x8D, 0x97, 0x3F, 0x67, 0x95, 0x59, 0xA6, 0xA3, 0xAA, 0xD7, 0x7E, 0xD5, 0x13, 0x2D, 0x01, 0x50, 0xC0, 0x14, 0xC3, 0xEC, 0x3A, 0x39, 0x5F, 0x01, 0x7E, 0x7A, 0xCF, 0xE3, 0xEA, + 0xBF, 0xCA, 0x44, 0x91, 0x0C, 0xA0, 0x6F, 0xF3, 0x35, 0x42, 0xEC, 0xCE, 0x62, 0x41, 0x97, 0x47, 0x42, 0x35, 0x7D, 0x37, 0xF5, 0xC2, 0x84, 0xBF, 0x0F, 0xE1, 0xA7, 0x4B, 0x50, 0xC0, 0x73, 0x55, + 0x13, 0x72, 0x13, 0x3A, 0xF2, 0xDD, 0x41, 0xE2, 0x1B, 0xAF, 0xC9, 0xC5, 0x90, 0xEE, 0x6E, 0xBC, 0x4A, 0xCE, 0x73, 0x1E, 0xF5, 0x66, 0x15, 0x6C, 0xA0, 0x37, 0x55, 0xDC, 0x49, 0x3C, 0x13, 0x70, + 0x28, 0xAF, 0x3B, 0x3D, 0xE5, 0xB0, 0x0B, 0xD6, 0xCB, 0x3D, 0x9A, 0x87, 0xD0, 0x15, 0x1F, 0x88, 0x7C, 0x67, 0x68, 0xBC, 0x6C, 0xA0, 0x2A, 0x94, 0xFB, 0x20, 0x86, 0x55, 0x1A, 0x0F, 0x89, 0xBA, + 0x26, 0x15, 0x4E, 0x9D, 0x45, 0x06, 0xAD, 0x9F, 0xAF, 0x39, 0xF5, 0x72, 0x3E, 0x23, 0x4E, 0x06, 0xCF, 0xDE, 0xD6, 0x9D, 0x4E, 0xE4, 0x14, 0x6B, 0x73, 0xE5, 0xDC, 0x1E, 0x41, 0x52, 0xA2, 0xA3, + 0x15, 0x9D, 0x73, 0xDB, 0xC8, 0x33, 0xD3, 0xD4, 0x17, 0xCD, 0x5C, 0xF7, 0xFB, 0x3D, 0xC7, 0x74, 0x5C, 0xEE, 0xD4, 0xDC, 0x0F, 0x5B, 0x1C, 0x6D, 0x6B, 0x69, 0xC1, 0x76, 0x41, 0x57, 0xEA, 0x43, + 0xDF, 0x9D, 0xBB, 0x44, 0x2E, 0xFA, 0x39, 0xD1, 0xD0, 0x16, 0x2E, 0x87, 0xC2, 0xD3, 0x0C, 0x50, 0x12, 0xFD, 0x16, 0xD8, 0x69, 0xC8, 0xA1, 0xFC, 0xBB, 0x45, 0xED, 0xCC, 0x8E, 0x18, 0x13, 0xB2, + 0xB1, 0x90, 0xA9, 0x61, 0xF9, 0xFC, 0x86, 0x59, 0x1D, 0x3A, 0xBC, 0x53, 0x88, 0xAF, 0x67, 0x8F, 0xF0, 0x3D, 0xA7, 0x8B, 0x7C, 0xC0, 0xF6, 0x18, 0x57, 0x21, 0xC0, 0xDF, 0x33, 0xCC, 0x90, 0x64, + 0x35, 0x22, 0x5D, 0xF2, 0x61, 0x10, 0x02, 0xDF, 0x12, 0x0E, 0x83, 0x56, 0x65, 0x32, 0x29, 0x2D, 0xEA, 0x3D, 0x8A, 0xCD, 0x10, 0x9A, 0x0D, 0xFF, 0xAB, 0x3B, 0x0B, 0x43, 0x01, 0x27, 0x96, 0xDB, + 0x5B, 0x50, 0x68, 0x3F, 0xB4, 0xC2, 0xD2, 0x50, 0xDA, 0xB7, 0x6A, 0xAE, 0x35, 0xA4, 0x8E, 0x8C, 0x8D, 0x4A, 0x5C, 0xC1, 0x54, 0x75, 0x97, 0x45, 0xF0, 0xA1, 0x23, 0x0F, 0x6C, 0xA9, 0xDD, 0x9C, + 0x99, 0xE2, 0xF8, 0x0E, 0xDC, 0x83, 0x30, 0x4C, 0xE0, 0x1E, 0x98, 0xF6, 0xC9, 0x48, 0x95, 0x29, 0xA8, 0x22, 0xF9, 0x00, 0x33, 0xC2, 0x28, 0x31, 0x5E, 0xB2, 0xFC, 0xC8, 0xDB, 0xA3, 0x82, 0xED, + 0x43, 0x01, 0xE0, 0x76, 0x07, 0xA5, 0xB0, 0x76, 0xC7, 0x25, 0xF1, 0x24, 0x99, 0x4F, 0x18, 0xA9, 0x97, 0xD2, 0xC5, 0xBB, 0xF9, 0xA3, 0x24, 0x60, 0x52, 0x65, 0x10, 0x8A, 0xCB, 0xF4, 0x61, 0x0F, + 0xA1, 0xC3, 0x37, 0x44, 0x08, 0x85, 0x0A, 0x08, 0x64, 0xE2, 0xB6, 0x10, 0x17, 0xEB, 0xEC, 0x1F, 0xBA, 0xB8, 0x9D, 0xE3, 0xAB, 0x1B, 0x93, 0xCE, 0x49, 0x18, 0xB9, 0xE2, 0xC9, 0xE3, 0xFE, 0x45, + 0x67, 0x58, 0x06, 0x2A, 0x9F, 0x88, 0x2B, 0x28, 0x33, 0x18, 0x27, 0x1F, 0x4B, 0x95, 0x52, 0xFC, 0xF3, 0x26, 0x24, 0xA9, 0xFD, 0xAA, 0x44, 0xC6, 0x5C, 0x60, 0xE2, 0xB3, 0x64, 0x8B, 0xEF, 0x1F, + 0x17, 0xD0, 0xB7, 0xC7, 0x48, 0x69, 0xEE, 0x0B, 0x53, 0xC4, 0xA6, 0x2A, 0x24, 0x84, 0x5D, 0xCE, 0xA5, 0xBC, 0xBF, 0x93, 0xB9, 0x2E, 0x4C, 0x26, 0x64, 0x85, 0x84, 0xE3, 0x34, 0x79, 0x28, 0x2E, + 0x6C, 0x8B, 0x1D, 0x8F, 0xE2, 0x11, 0x81, 0xBD, 0x9C, 0xF7, 0x5F, 0x8A, 0x96, 0x17, 0x24, 0xD4, 0xC4, 0x30, 0x97, 0x79, 0xF1, 0xF1, 0xB7, 0x75, 0xD2, 0x54, 0xF7, 0x0B, 0xD1, 0x76, 0x9C, 0xC7, + 0xC0, 0xED, 0xD2, 0xA9, 0x5F, 0xE5, 0xC9, 0xD8, 0x4B, 0x16, 0xF7, 0xC5, 0x4D, 0x85, 0xCC, 0xE4, 0xC8, 0xA1, 0x82, 0x81, 0x08, 0x09, 0xED, 0x81, 0xE9, 0x7D, 0x07, 0x48, 0x84, 0xEE, 0xDF, 0x40, + 0x1C, 0xCA, 0xCD, 0xAE, 0xAD, 0x82, 0xC1, 0x4D, 0x06, 0xB6, 0x8A, 0xEA, 0x6C, 0xE1, 0x4B, 0x86, 0x1B, 0x0C, 0xFD, 0x16, 0x09, 0x0C, 0xBB, 0xF4, 0x69, 0xC5, 0xE0, 0x84, 0x31, 0x4C, 0x0D, 0x8D, + 0x39, 0x60, 0xEA, 0x06, 0xA3, 0x42, 0x6D, 0x8B, 0x3F, 0xE7, 0x62, 0xE0, 0x0D, 0x09, 0xBD, 0xA3, 0x74, 0xF3, 0xAE, 0x2C, 0xBE, 0xDE, 0x28, 0x38, 0xFF, 0x89, 0xD8, 0x1D, 0xEB, 0x30, 0x13, 0x09, + 0x0E, 0x44, 0x19, 0x9A, 0xED, 0x60, 0x49, 0x63, 0xEA, 0xF9, 0x19, 0x91, 0x4C, 0xE0, 0x4F, 0x20, 0x7A, 0xC8, 0x2C, 0xD4, 0x35, 0x1F, 0xEF, 0x7B, 0x2D, 0x94, 0x39, 0x30, 0x66, 0xFE, 0x4D, 0x44, + 0xE3, 0xCC, 0x59, 0x52, 0xE7, 0x5E, 0xB6, 0xF3, 0x71, 0x40, 0x58, 0x91, 0x5D, 0xE0, 0xEE, 0x18, 0x4D, 0x8C, 0x55, 0x30, 0x0F, 0x57, 0x6A, 0x8B, 0x82, 0xA8, 0x63, 0xE8, 0x1A, 0xF3, 0x34, 0x17, + 0xBD, 0x4C, 0xFC, 0x94, 0xE7, 0xA6, 0x12, 0x63, 0xB3, 0x9F, 0x01, 0xF6, 0xE2, 0xE7, 0x07, 0x48, 0xB6, 0xE5, 0xE5, 0x9C, 0xF6, 0xCA, 0x01, 0xB0, 0x02, 0x8C, 0x93, 0xBB, 0xBC, 0xEB, 0xC5, 0x48, + 0xF9, 0x87, 0xF1, 0x07, 0x55, 0xBF, 0x33, 0xCA, 0x58, 0x5C, 0xB4, 0x1C, 0xF5, 0x78, 0xDF, 0x5F, 0xFE, 0x37, 0x92, 0x4E, 0x3C, 0x2C, 0x07, 0x2E, 0xD1, 0xDA, 0xC9, 0x16, 0x21, 0x76, 0x97, 0x29, + 0x71, 0xE7, 0x9B, 0x62, 0xFB, 0x20, 0x8F, 0x1A, 0x73, 0xBF, 0x03, 0x61, 0xE2, 0x99, 0x3D, 0xCC, 0xCD, 0x31, 0x10, 0xC3, 0x4D, 0x83, 0x9D, 0x18, 0xDD, 0x43, 0xA5, 0xE8, 0xF0, 0xD9, 0x41, 0xE9, + 0x9A, 0xDC, 0xF4, 0x41, 0x40, 0x5F, 0x32, 0x10, 0x76, 0x71, 0xB2, 0xD8, 0xB2, 0x24, 0x4F, 0x7B, 0xA9, 0x2D, 0xCE, 0xD5, 0x87, 0xA2, 0x10, 0xFE, 0x8F, 0xF4, 0x3C, 0x61, 0x6A, 0xCB, 0x5E, 0x76, + 0x6E, 0x6A, 0xF2, 0xCE, 0xB0, 0x35, 0x99, 0xBA, 0x3D, 0xE3, 0x76, 0xEB, 0x57, 0x35, 0xEF, 0x16, 0x14, 0x39, 0x53, 0xD1, 0xFD, 0xDB, 0x7E, 0x9F, 0x28, 0x74, 0xB0, 0xD6, 0x08, 0x3D, 0xD7, 0xEC, + 0x43, 0x86, 0xAE, 0x00, 0x3F, 0x51, 0xCC, 0xF2, 0xD2, 0x1E, 0xF6, 0x05, 0x91, 0x63, 0xC5, 0x15, 0x21, 0x74, 0x42, 0x3F, 0x57, 0x11, 0x9D, 0x0F, 0xCE, 0x62, 0x7D, 0x76, 0x3D, 0x81, 0xC1, 0x0A, + 0xA1, 0x32, 0x9F, 0x74, 0xC8, 0xD4, 0x45, 0x43, 0x7B, 0xA6, 0x71, 0x8A, 0x33, 0xDB, 0x6E, 0x79, 0x37, 0x51, 0x72, 0xB2, 0xAE, 0x35, 0x91, 0x82, 0x19, 0x78, 0xD5, 0x20, 0x82, 0x4E, 0x2D, 0x2F, + 0xF8, 0x98, 0xB7, 0xF4, 0xC8, 0x67, 0xFF, 0x46, 0x27, 0x22, 0xBC, 0x07, 0xEA, 0xDA, 0xD3, 0x89, 0xA9, 0x10, 0xB6, 0xF6, 0x54, 0x29, 0xDA, 0x12, 0x97, 0x35, 0xFE, 0x04, 0x9E, 0x3E, 0xCB, 0x38, + 0x89, 0xF6, 0x04, 0x7C, 0xF2, 0xBD, 0x2A, 0x88, 0xD5, 0x0A, 0x65, 0x1B, 0x32, 0x35, 0xD2, 0x48, 0x0E, 0x1D, 0xA5, 0xA3, 0x52, 0x47, 0xFA, 0x76, 0xC8, 0x31, 0x73, 0x63, 0x99, 0xD3, 0x7E, 0x8D, + 0x03, 0x3C, 0x1D, 0x05, 0x1C, 0x9B, 0x6A, 0x99, 0xAB, 0x80, 0xB1, 0x31, 0x3F, 0xA2, 0x4C, 0x5C, 0x59, 0x76, 0x6E, 0x6C, 0x51, 0xA3, 0x8F, 0xE9, 0xF1, 0x18, 0x6A, 0x76, 0x7E, 0xEB, 0xD0, 0xD8, + 0x80, 0x01, 0xAE, 0x02, 0x46, 0xCD, 0x4E, 0xBE, 0x2C, 0x97, 0x9D, 0xE8, 0x2C, 0x30, 0xBB, 0xDB, 0x98, 0xB4, 0x74, 0x4F, 0x11, 0xF9, 0xE6, 0x39, 0xED, 0xDD, 0x8C, 0x19, 0x4D, 0x79, 0x11, 0x20, + 0x1A, 0x8F, 0xA7, 0x45, 0x99, 0x1B, 0x4D, 0x8A, 0x57, 0x09, 0xB6, 0x2A, 0x21, 0xB6, 0x3B, 0x97, 0x62, 0x91, 0x3D, 0x36, 0xCE, 0x99, 0x5C, 0x2D, 0x6B, 0x79, 0x15, 0x1E, 0x8D, 0x83, 0x83, 0x8C, + 0xD1, 0xF3, 0x88, 0x40, 0xA9, 0x41, 0x72, 0x55, 0xDD, 0x16, 0x6B, 0x7A, 0x35, 0x84, 0x49, 0x90, 0x03, 0xFB, 0x62, 0x56, 0x11, 0x40, 0x4C, 0x95, 0xB9, 0x60, 0xDF, 0x0D, 0xB1, 0xBC, 0xF1, 0x57, + 0x4B, 0x09, 0x65, 0xDB, 0xD8, 0x34, 0xEE, 0x14, 0x81, 0x17, 0xD5, 0xE0, 0x5A, 0x7C, 0xC7, 0xCC, 0x1A, 0x86, 0x56, 0x18, 0xA2, 0xBE, 0x48, 0x54, 0xDB, 0x89, 0x35, 0xCD, 0xA1, 0xE6, 0x8B, 0xD8, + 0xD0, 0x9E, 0x72, 0xF0, 0xAC, 0x90, 0x53, 0xC8, 0x82, 0xC4, 0xAB, 0xA4, 0x00, 0x4A, 0x61, 0x4D, 0x10, 0x50, 0x53, 0x00, 0xB6, 0x17, 0x6C, 0xA1, 0xF3, 0x24, 0xE2, 0x2E, 0x78, 0x24, 0x29, 0x9F, + 0x9C, 0x40, 0x75, 0x5B, 0x71, 0xD8, 0x2B, 0x67, 0x95, 0x47, 0xF0, 0x6A, 0xD4, 0x8B, 0xE6, 0x6D, 0x68, 0x07, 0x2C, 0x93, 0x90, 0x23, 0x3C, 0x93, 0x3F, 0x80, 0xA1, 0x4F, 0x8D, 0x4A, 0x6B, 0x0B, + 0x4E, 0x19, 0x70, 0xE1, 0xAC, 0xC1, 0xBE, 0xA7, 0xF5, 0xD3, 0xBE, 0x22, 0x44, 0x48, 0xF8, 0x57, 0xBA, 0xB6, 0x8A, 0xEF, 0xA6, 0xD8, 0xCB, 0x81, 0x9B, 0x64, 0x29, 0x4A, 0x12, 0x99, 0x79, 0x16, + 0xCD, 0xBF, 0x56, 0xE9, 0xA8, 0xD0, 0x02, 0xDD, 0x06, 0x5F, 0x12, 0xC6, 0x18, 0x23, 0xF4, 0xFC, 0x21, 0x45, 0x08, 0x23, 0x2E, 0x43, 0x1F, 0x0B, 0x68, 0x98, 0x47, 0x5B, 0xB5, 0xDD, 0x0D, 0x7D, + 0x52, 0x8E, 0x84, 0x0C, 0x22, 0x80, 0x9A, 0xF7, 0xE1, 0x53, 0x63, 0x72, 0x4A, 0x61, 0x3A, 0xCC, 0xFB, 0xE2, 0xB3, 0x74, 0x38, 0xC1, 0x59, 0xCE, 0x14, 0xCB, 0x0C, 0x98, 0xBF, 0xD4, 0x99, 0xC0, + 0x8D, 0xAC, 0x0C, 0xF4, 0x5D, 0x82, 0x1C, 0xC2, 0xFA, 0x47, 0x31, 0x9B, 0x6F, 0xB4, 0xCE, 0xD7, 0xE5, 0x98, 0x5E, 0xC8, 0x27, 0x4D, 0xE0, 0x90, 0x71, 0xD3, 0xC1, 0x0D, 0xA5, 0xBF, 0x9E, 0x52, + 0x2B, 0x01, 0xCE, 0x91, 0xD6, 0x6B, 0x91, 0x79, 0x5D, 0x3D, 0x22, 0xC0, 0x04, 0x83, 0x45, 0x42, 0x75, 0xDD, 0x2B, 0xBD, 0xD7, 0xC2, 0xDC, 0xC4, 0xA1, 0x67, 0xE5, 0xD7, 0xFC, 0xDB, 0xB9, 0xF6, + 0x20, 0x8C, 0xD4, 0xC9, 0xA4, 0x85, 0xFA, 0xAE, 0xB8, 0x09, 0xA7, 0x71, 0x1D, 0xAC, 0x28, 0x65, 0xCE, 0xD4, 0x30, 0x64, 0x74, 0xB2, 0x2B, 0x44, 0x48, 0xF8, 0x5D, 0xF3, 0x34, 0x17, 0xF3, 0xFA, + 0xCE, 0x1C, 0x05, 0xD4, 0x27, 0x03, 0xED, 0x31, 0x30, 0x42, 0xA0, 0x5D, 0xE0, 0x36, 0x27, 0x40, 0x13, 0x01, 0x88, 0xEC, 0xB4, 0x45, 0xBB, 0x25, 0x5D, 0xC7, 0x6E, 0xE8, 0x44, 0x3F, 0x73, 0x31, + 0x17, 0xF8, 0x35, 0x1F, 0x17, 0x60, 0x31, 0x75, 0x55, 0x4F, 0xEB, 0x00, 0xB7, 0xFF, 0x54, 0xD8, 0x07, 0x86, 0xF3, 0x05, 0xCD, 0xE1, 0x8C, 0xD5, 0xEC, 0x56, 0xEC, 0x09, 0x62, 0xA3, 0xE0, 0x44, + 0x82, 0xDC, 0xE3, 0x62, 0x2D, 0x04, 0x0D, 0x24, 0xC4, 0x0F, 0x2E, 0x8A, 0x14, 0xA4, 0x47, 0x65, 0x9D, 0x6C, 0x56, 0x1F, 0x2F, 0xFE, 0xE6, 0x8F, 0x8D, 0x3D, 0xE5, 0x11, 0xB2, 0x3E, 0x8B, 0x17, + 0x2A, 0x01, 0xA3, 0xED, 0xA4, 0xD3, 0x78, 0x0E, 0x74, 0xC6, 0x77, 0x24, 0x43, 0x30, 0xE9, 0xAE, 0xFF, 0x01, 0x9F, 0xE0, 0x7B, 0xE3, 0xD3, 0x3F, 0x32, 0x2F, 0x9C, 0xE2, 0x21, 0x4B, 0x9D, 0x9C, + 0xFF, 0x99, 0xD0, 0x5A, 0x59, 0xE4, 0x75, 0x51, 0x43, 0x2A, 0xE7, 0x6F, 0x4C, 0xD4, 0xF8, 0xDD, 0x51, 0x52, 0x0F, 0xFE, 0x81, 0x1B, 0x4B, 0x93, 0xCD, 0x62, 0x19, 0xC8, 0x1B, 0x63, 0xB1, 0xD6, + 0x27, 0x78, 0x5C, 0x2A, 0x0F, 0xC2, 0x2E, 0x3A, 0xEA, 0x86, 0xCE, 0xEE, 0x1F, 0x7F, 0xBC, 0x4E, 0xFC, 0xB4, 0x6D, 0xDF, 0xBC, 0xD8, 0x8A, 0x02, 0xF3, 0xB4, 0xE6, 0x7C, 0x5F, 0xF2, 0xE8, 0xDC, + 0x68, 0xBF, 0x16, 0xC7, 0x46, 0x99, 0xBB, 0xB6, 0x28, 0x90, 0x2F, 0x72, 0xC3, 0xDE, 0xBC, 0x8B, 0xF5, 0xDF, 0x70, 0x6D, 0x47, 0xA6, 0x05, 0xA1, 0x07, 0xDA, 0xA0, 0x01, 0x41, 0x39, 0xCE, 0x40, + 0xF0, 0xD4, 0x6D, 0x8D, 0x6D, 0xC7, + }, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 3293, + .sig = { + 0xB0, 0x55, 0xB0, 0xE1, 0x76, 0x10, 0xBF, 0x54, 0xB3, 0x3B, 0x96, 0x09, 0x8D, 0x79, 0x6E, 0x98, 0xF7, 0x89, 0x9F, 0x48, 0x56, 0xCB, 0xC8, 0xD7, 0x04, 0xF9, 0xD7, 0x77, 0x8C, 0x18, 0x77, 0xF1, + 0xE1, 0x24, 0xBF, 0x62, 0xA0, 0xD1, 0x7F, 0x01, 0x3B, 0xE4, 0x34, 0x0F, 0xD5, 0x7B, 0x4F, 0xA6, 0x22, 0x2D, 0x9C, 0xDB, 0x90, 0x28, 0xE8, 0xB0, 0x2B, 0x92, 0x6E, 0x15, 0x54, 0xD1, 0x45, 0xF4, + 0x47, 0x98, 0xAA, 0xC2, 0xFA, 0xA2, 0x03, 0x3C, 0x4A, 0xEF, 0xB6, 0xCC, 0xB6, 0xCF, 0xE5, 0xC2, 0xA6, 0x23, 0x8E, 0xE7, 0x9C, 0x5C, 0xC2, 0xF0, 0xE8, 0x04, 0xBE, 0xD1, 0x7F, 0x75, 0xC1, 0xF3, + 0x99, 0x4D, 0xD7, 0xE7, 0xA0, 0xF2, 0xA7, 0x03, 0x4C, 0x0C, 0x8C, 0x98, 0x64, 0x80, 0x40, 0x57, 0xE2, 0xE5, 0x57, 0x67, 0x3F, 0xDF, 0xD6, 0x64, 0x35, 0x6F, 0xAB, 0xD0, 0x51, 0xF9, 0x07, 0x5B, + 0x34, 0x00, 0xA0, 0xC7, 0xE8, 0x45, 0x59, 0x55, 0x3E, 0xDF, 0x98, 0x9B, 0xFF, 0xD2, 0x11, 0x2B, 0x29, 0x60, 0x22, 0x03, 0x06, 0x6B, 0xDE, 0xA7, 0x84, 0x35, 0xEB, 0xC6, 0xE3, 0x81, 0x8C, 0xC9, + 0x2D, 0x61, 0xBC, 0xC1, 0x25, 0xA8, 0x57, 0x5B, 0x5A, 0x8A, 0xEE, 0x42, 0x25, 0xFB, 0x9C, 0x62, 0x48, 0x3F, 0x3E, 0xD1, 0x18, 0x5A, 0x6A, 0x96, 0x82, 0x2E, 0x5E, 0xFC, 0x1B, 0xA7, 0xCD, 0x8D, + 0x5F, 0xD8, 0xCC, 0x18, 0x7D, 0x2A, 0x26, 0x69, 0xCA, 0xDF, 0x58, 0xFA, 0xD6, 0x62, 0x89, 0x79, 0x4C, 0x96, 0x48, 0x5B, 0x2C, 0x46, 0x45, 0xC7, 0xD3, 0xD3, 0x56, 0x84, 0xB7, 0x42, 0x9B, 0x5E, + 0xF3, 0x15, 0x45, 0x76, 0x99, 0xBE, 0x80, 0x30, 0xBC, 0x3D, 0xEB, 0x81, 0x66, 0x60, 0x2A, 0xC5, 0x48, 0x19, 0x82, 0x48, 0x83, 0xA2, 0x46, 0xC8, 0xA1, 0xA3, 0x4F, 0xC8, 0x9B, 0x2F, 0xE0, 0x32, + 0x9B, 0x5C, 0xA0, 0x5D, 0x4E, 0x14, 0xB6, 0xDF, 0xFC, 0x21, 0x44, 0x60, 0x6A, 0xB3, 0x60, 0xBB, 0x3B, 0x8A, 0xC5, 0xA1, 0x78, 0x99, 0x8B, 0x46, 0x21, 0x81, 0x81, 0xCA, 0xC8, 0xDE, 0x4C, 0x29, + 0x48, 0x30, 0xD4, 0x9D, 0x8F, 0x00, 0xEC, 0x12, 0xC3, 0xD3, 0xAC, 0x7B, 0x4A, 0x2C, 0x30, 0x17, 0x58, 0xE6, 0x8A, 0x56, 0x81, 0x17, 0x7F, 0xF2, 0xA7, 0x5D, 0x1D, 0x4B, 0xF1, 0xC9, 0x26, 0x88, + 0x0B, 0x34, 0xB7, 0x28, 0xF7, 0xC3, 0x2E, 0x40, 0x60, 0x99, 0xD9, 0x5A, 0xB4, 0x48, 0x92, 0xF7, 0x48, 0xAA, 0xFE, 0xB5, 0x5B, 0x26, 0xBE, 0x31, 0x75, 0x12, 0xB0, 0x37, 0x7D, 0xBE, 0x89, 0x1A, + 0xC5, 0x45, 0x6A, 0x92, 0x4C, 0x36, 0x83, 0x9B, 0xC8, 0x01, 0xDB, 0x2A, 0xC5, 0xB7, 0x11, 0x0A, 0x9B, 0xAF, 0x4C, 0x3C, 0x49, 0xD0, 0x05, 0x39, 0x3C, 0xDF, 0xFA, 0xD4, 0xF9, 0x68, 0x61, 0x20, + 0xF4, 0xFD, 0xE0, 0x16, 0x8A, 0x9E, 0x45, 0x8E, 0x72, 0x9F, 0x4B, 0x0A, 0xE1, 0xA4, 0xC4, 0x12, 0x4C, 0xA3, 0x4D, 0xF5, 0xB6, 0x3B, 0xC2, 0xE7, 0xCB, 0xEE, 0x01, 0xA3, 0x8D, 0x31, 0xA0, 0xED, + 0x8D, 0x3C, 0x4C, 0x38, 0x03, 0xC3, 0xC2, 0x4C, 0x5C, 0xAD, 0xEB, 0xE3, 0xE9, 0x1A, 0x8D, 0x2E, 0x1B, 0xFC, 0xF0, 0x50, 0x8A, 0x27, 0x88, 0xD8, 0x9D, 0xFE, 0xA2, 0x0F, 0xD6, 0x38, 0x18, 0xB8, + 0x39, 0x60, 0xA6, 0xCF, 0x93, 0x08, 0x72, 0xB9, 0x57, 0x85, 0x57, 0x50, 0x88, 0xCF, 0x7E, 0x8B, 0x63, 0xA1, 0x89, 0x5A, 0x8C, 0x1C, 0x77, 0xA8, 0x4C, 0xB9, 0xCC, 0x6B, 0xD1, 0xD5, 0xFA, 0x93, + 0x96, 0x77, 0xAF, 0x17, 0xEE, 0xBE, 0x2D, 0x2E, 0xE6, 0x84, 0xC6, 0x60, 0x15, 0xF1, 0xBB, 0x14, 0x2A, 0x72, 0x77, 0x79, 0x58, 0x0D, 0xA1, 0xBC, 0x5E, 0x97, 0x5A, 0xA5, 0x6E, 0xF5, 0xD7, 0x7A, + 0x84, 0x07, 0xE5, 0x06, 0xA5, 0xDE, 0xEE, 0xA5, 0xE8, 0xB0, 0x79, 0x7F, 0x10, 0x64, 0x60, 0x05, 0x64, 0x80, 0x22, 0x21, 0x3C, 0xCB, 0x86, 0xA7, 0x7D, 0xF5, 0xD7, 0xB3, 0x16, 0xE8, 0x5D, 0x55, + 0xB9, 0xDA, 0x0F, 0xDF, 0xD5, 0xF2, 0x35, 0x52, 0xDD, 0x47, 0xCC, 0xFA, 0x96, 0x4A, 0xC3, 0x9E, 0xE6, 0x84, 0xBD, 0x63, 0x79, 0x3B, 0xB7, 0xDC, 0xAB, 0x69, 0xBE, 0x7E, 0xD9, 0x4D, 0x8D, 0xDB, + 0xA1, 0x85, 0xE8, 0x0A, 0x7A, 0xAE, 0xE7, 0x4E, 0x87, 0x8F, 0x50, 0xA2, 0x13, 0xF3, 0xB4, 0xFF, 0xB6, 0x6E, 0x6D, 0x34, 0xA3, 0x9C, 0x0A, 0xAE, 0x2B, 0x1D, 0x61, 0x36, 0x6F, 0xE4, 0x03, 0x53, + 0x9C, 0x69, 0xA0, 0x88, 0x75, 0x1F, 0x56, 0x90, 0x1A, 0x10, 0xBC, 0x44, 0x23, 0x13, 0xA3, 0x5C, 0x2D, 0x83, 0x54, 0x76, 0xD0, 0xFA, 0xD4, 0x47, 0xC7, 0x70, 0x08, 0x0F, 0xA4, 0x1B, 0xF3, 0x8D, + 0x68, 0x5F, 0xB3, 0x1B, 0x11, 0xA7, 0xD2, 0xE6, 0xFB, 0x52, 0x67, 0x3D, 0x16, 0x87, 0x23, 0xE6, 0x89, 0x08, 0xC0, 0x67, 0x2A, 0x0F, 0x36, 0xE2, 0x5A, 0x19, 0x9E, 0x17, 0xA6, 0xFE, 0x5B, 0x8B, + 0x82, 0x5B, 0x96, 0xEA, 0xB7, 0xAB, 0x4B, 0x7D, 0x83, 0x81, 0xDB, 0xC5, 0x00, 0x31, 0xA5, 0xF2, 0xE0, 0x9E, 0x4B, 0xE8, 0x71, 0x53, 0x3A, 0xDC, 0x5D, 0x08, 0xD0, 0x09, 0x42, 0x9B, 0xBF, 0x5C, + 0x86, 0xF8, 0x12, 0x0D, 0x09, 0x5C, 0x8E, 0xEC, 0xBE, 0xF3, 0xE0, 0x99, 0xDE, 0x61, 0x8D, 0x43, 0x77, 0x24, 0x1B, 0x50, 0x36, 0x9E, 0xDE, 0x51, 0xAA, 0x74, 0xAB, 0x96, 0x65, 0x89, 0xE2, 0xC6, + 0x87, 0xD6, 0xC0, 0x9F, 0xAC, 0x9C, 0x6D, 0x6C, 0x54, 0x61, 0xF5, 0xA6, 0x30, 0x08, 0xE9, 0x83, 0x5F, 0xF4, 0xB5, 0xBD, 0x42, 0x65, 0xF1, 0x12, 0x8C, 0x09, 0x2C, 0x27, 0xD4, 0xDA, 0x50, 0x8F, + 0xD4, 0xF5, 0x0E, 0xFA, 0x74, 0xA7, 0x31, 0x57, 0x05, 0x9A, 0x4B, 0x2F, 0x41, 0xFE, 0x8B, 0xF9, 0x67, 0x16, 0x79, 0x69, 0xB9, 0x3B, 0xF5, 0x20, 0x45, 0x84, 0x26, 0x90, 0x32, 0x42, 0x9E, 0x35, + 0x77, 0x70, 0x4B, 0xDF, 0x68, 0x98, 0x00, 0xDD, 0x8B, 0xDE, 0x82, 0x6B, 0x74, 0xCE, 0xF5, 0x10, 0xA1, 0xE0, 0x87, 0x02, 0x3F, 0x09, 0x26, 0xE9, 0x7F, 0x37, 0x92, 0x6B, 0x16, 0xEF, 0x78, 0x6C, + 0x37, 0xEC, 0x21, 0xF2, 0x40, 0x71, 0x04, 0xD3, 0x95, 0x4A, 0x7A, 0x07, 0xC3, 0x0D, 0xE2, 0xD6, 0x78, 0x84, 0x02, 0xD7, 0x1A, 0x56, 0x2E, 0xA5, 0x4C, 0x79, 0xB4, 0x19, 0x7D, 0x20, 0x2C, 0x97, + 0x72, 0x5D, 0x2D, 0x8B, 0x7E, 0x73, 0x32, 0xF3, 0xFF, 0x1A, 0x6F, 0xAD, 0x49, 0xA4, 0xC0, 0x0C, 0xD1, 0xA4, 0x47, 0x65, 0x1B, 0x8E, 0x08, 0xD8, 0x50, 0x6B, 0xCA, 0x82, 0x3E, 0x10, 0xEF, 0x41, + 0x16, 0xE6, 0xCF, 0x49, 0x67, 0x5C, 0x43, 0x30, 0xA1, 0xDE, 0x19, 0x08, 0xDD, 0xB5, 0x9F, 0x7E, 0xA5, 0xF8, 0x9C, 0x94, 0xCE, 0x50, 0x0F, 0x82, 0xB4, 0x3C, 0xE7, 0x89, 0x15, 0x84, 0x73, 0xB9, + 0xE0, 0x79, 0x05, 0xD8, 0xE8, 0x61, 0x5E, 0xDE, 0xF0, 0x21, 0x38, 0x3F, 0xC3, 0x1D, 0x61, 0x8C, 0x5C, 0xE6, 0x25, 0x65, 0x3B, 0x40, 0xC2, 0x1B, 0xD7, 0xE0, 0xBC, 0x78, 0x3D, 0x93, 0xBE, 0xC1, + 0xB7, 0xA5, 0xB4, 0xBB, 0xC6, 0xC2, 0x81, 0xB7, 0x77, 0x55, 0x47, 0x39, 0x0E, 0xF3, 0xD3, 0x0E, 0x27, 0x73, 0x99, 0x36, 0x93, 0x08, 0xD8, 0xA1, 0xCD, 0xC2, 0xE1, 0xDB, 0xD6, 0xF1, 0x58, 0x97, + 0x0A, 0xC2, 0xAC, 0x5C, 0x2C, 0x94, 0x81, 0x97, 0x5B, 0x80, 0x95, 0x80, 0xC0, 0xEA, 0x89, 0x91, 0x2C, 0x07, 0x66, 0xF4, 0x58, 0x30, 0xA8, 0x96, 0x3F, 0xBB, 0x7E, 0x17, 0xD8, 0x43, 0x85, 0x17, + 0x5A, 0x6E, 0x07, 0x54, 0x68, 0x3C, 0xBF, 0xBB, 0xA6, 0x36, 0x45, 0x94, 0xF6, 0xB5, 0x00, 0x5C, 0x15, 0xBD, 0x5F, 0x85, 0x73, 0x2B, 0x5A, 0x63, 0xF2, 0x62, 0x67, 0xAB, 0x17, 0x04, 0x8C, 0x61, + 0x99, 0x20, 0x00, 0x19, 0xAD, 0xD6, 0xA4, 0xD1, 0xAC, 0xD0, 0x40, 0x5C, 0x38, 0x76, 0x66, 0xE8, 0x71, 0x11, 0xB9, 0x82, 0x5A, 0xFB, 0x97, 0x51, 0xCD, 0x3F, 0x9D, 0x8A, 0x45, 0xC6, 0xB2, 0x08, + 0xD2, 0xD3, 0x33, 0xB6, 0xC5, 0x9F, 0x98, 0xBC, 0xF2, 0x84, 0xC8, 0x54, 0xCF, 0x7D, 0x4F, 0x67, 0x54, 0xFD, 0x75, 0xEE, 0x06, 0x8C, 0x88, 0x67, 0x8E, 0xE7, 0x56, 0x5B, 0x47, 0xB3, 0x6E, 0x68, + 0xA1, 0xFD, 0x7B, 0xB6, 0x0E, 0x2A, 0x8E, 0x0D, 0xF7, 0x12, 0x70, 0x20, 0xF5, 0xC6, 0x27, 0x7B, 0x3E, 0xE0, 0x58, 0x77, 0x3F, 0x9B, 0xBF, 0x1D, 0xC2, 0xE3, 0x98, 0xBC, 0x30, 0x12, 0x02, 0x12, + 0x1C, 0x69, 0x9C, 0x00, 0x37, 0x9D, 0x83, 0x50, 0x09, 0x96, 0x26, 0xF9, 0x09, 0x23, 0x65, 0x92, 0x40, 0x08, 0xB1, 0xA9, 0xCD, 0x9F, 0x87, 0x87, 0x82, 0x2B, 0xEE, 0x96, 0x1A, 0xBA, 0x23, 0x9C, + 0xDC, 0xB4, 0x18, 0xE9, 0x38, 0x60, 0xEF, 0x34, 0x8A, 0x5E, 0x96, 0x45, 0x38, 0x9A, 0x0A, 0x87, 0x8D, 0x39, 0x4F, 0x36, 0x5A, 0xEB, 0xFE, 0x28, 0x0B, 0xEE, 0x68, 0x74, 0xA3, 0x05, 0x4C, 0xD9, + 0x8C, 0xBD, 0x87, 0x16, 0x66, 0x28, 0x04, 0x72, 0x9F, 0xD4, 0x6F, 0xCE, 0xA9, 0xC4, 0xCF, 0x92, 0x9F, 0x2F, 0x12, 0x00, 0x06, 0xCE, 0xBC, 0xC0, 0xBF, 0x75, 0x69, 0x2D, 0x63, 0xC0, 0x44, 0x63, + 0x5D, 0x1A, 0x1D, 0xB6, 0x1A, 0xD1, 0x78, 0x94, 0x15, 0xE5, 0xF2, 0x24, 0x2B, 0x74, 0x00, 0xA8, 0xA7, 0x93, 0x68, 0xED, 0x60, 0x2C, 0x33, 0x64, 0x92, 0xF2, 0x70, 0x34, 0x5B, 0xE9, 0x8B, 0x2D, + 0xD6, 0xEA, 0x8E, 0x4C, 0x53, 0xAC, 0xA3, 0x6E, 0x3C, 0x9B, 0xA2, 0x88, 0xF2, 0x75, 0x86, 0x13, 0x4C, 0xF0, 0xB5, 0xCA, 0x9B, 0xA1, 0xEE, 0xDF, 0x20, 0xD1, 0xAB, 0x4F, 0x2D, 0x08, 0xF3, 0xB0, + 0x42, 0xDB, 0x89, 0xDE, 0xCF, 0xFD, 0xD2, 0x38, 0x54, 0xF3, 0x51, 0x20, 0xAD, 0xDE, 0x16, 0x03, 0x33, 0x5D, 0x56, 0x8D, 0xA9, 0x58, 0x91, 0xCF, 0x3A, 0xB2, 0x1D, 0x9A, 0xFA, 0xF6, 0x6C, 0x28, + 0x6C, 0x13, 0x00, 0x01, 0x9C, 0xA9, 0xBA, 0xF2, 0xFF, 0x3F, 0x67, 0x25, 0x23, 0x0C, 0x4B, 0x26, 0x98, 0x92, 0xF7, 0xA3, 0xDF, 0xD6, 0xEA, 0xB7, 0x4C, 0x31, 0x4A, 0x86, 0xF8, 0xB4, 0x7E, 0xAE, + 0x49, 0xF4, 0x19, 0xE4, 0xA2, 0x91, 0x7B, 0x98, 0x4F, 0xE9, 0xA0, 0x03, 0x32, 0xAF, 0xB7, 0xA5, 0x6E, 0x5E, 0x67, 0x52, 0x23, 0xAE, 0xCC, 0x50, 0x34, 0x20, 0xAF, 0x8B, 0x39, 0xFA, 0xA9, 0x20, + 0xE3, 0xAD, 0xA1, 0xA4, 0x3C, 0xE7, 0xBD, 0x1F, 0x7D, 0xF2, 0x30, 0x1C, 0x90, 0x27, 0xCC, 0x1C, 0xE5, 0x66, 0x6E, 0xB0, 0x93, 0x62, 0x10, 0xAF, 0xA5, 0x9E, 0x10, 0xF3, 0x07, 0xCA, 0x1F, 0x78, + 0x63, 0xED, 0xD6, 0xC3, 0xBB, 0x8F, 0x5D, 0x63, 0xC0, 0xCF, 0x0E, 0xA8, 0xF0, 0x6E, 0xF0, 0x8C, 0xCC, 0x24, 0xC1, 0x4F, 0x29, 0x5D, 0xD2, 0x86, 0xFD, 0x9F, 0x4E, 0x71, 0x02, 0x10, 0x9D, 0x53, + 0xFF, 0x5E, 0xFF, 0x4A, 0x01, 0xDC, 0xAA, 0xD5, 0xFB, 0x60, 0x55, 0xA0, 0x70, 0x3C, 0xD4, 0x71, 0xB2, 0x0B, 0x5F, 0xA4, 0x56, 0x0B, 0xDE, 0xAA, 0x13, 0x13, 0xC7, 0x64, 0x7A, 0xE7, 0x56, 0xAE, + 0x85, 0x91, 0x57, 0x9E, 0xA5, 0x12, 0x0E, 0x09, 0xD6, 0x79, 0x48, 0x40, 0x62, 0x9B, 0x9F, 0xEF, 0xEF, 0xC2, 0x0D, 0xB5, 0x94, 0xBA, 0xDC, 0xD1, 0x29, 0xEC, 0x49, 0x1C, 0x3C, 0xF7, 0x5A, 0xB4, + 0x0C, 0x47, 0x2A, 0xD2, 0x2C, 0x2D, 0xED, 0xBC, 0x77, 0xBA, 0x26, 0x71, 0xC8, 0x43, 0x48, 0x65, 0x60, 0xDC, 0x76, 0x52, 0x31, 0xBF, 0x5F, 0xDC, 0xDB, 0xCC, 0x77, 0xC8, 0x30, 0x0F, 0x9D, 0x2B, + 0x53, 0xEC, 0x34, 0x46, 0xD8, 0x2F, 0x08, 0x7B, 0x89, 0xBD, 0x99, 0x2F, 0x7A, 0xB0, 0xA7, 0x80, 0xB5, 0x38, 0x81, 0x18, 0xBB, 0xF1, 0x7C, 0xCB, 0xEC, 0x2D, 0x19, 0x6F, 0x3E, 0xDC, 0x47, 0x8F, + 0xB9, 0x47, 0xD8, 0x30, 0x2B, 0x04, 0x0A, 0x60, 0xD0, 0xBA, 0xB8, 0x5C, 0x1C, 0x5C, 0x47, 0x4E, 0xAB, 0x41, 0xE0, 0x64, 0x41, 0x06, 0x95, 0xC6, 0x0E, 0x1A, 0xCE, 0xE7, 0x9E, 0x13, 0x7D, 0x70, + 0x2E, 0x4A, 0x31, 0x39, 0x68, 0xA5, 0x57, 0xB9, 0x7C, 0xE6, 0x43, 0x31, 0x88, 0x8B, 0x52, 0x89, 0xCC, 0xB3, 0x7A, 0x66, 0x25, 0xE5, 0x22, 0x73, 0x71, 0x1B, 0x84, 0x64, 0x58, 0xD5, 0xD8, 0xBA, + 0x1A, 0xE4, 0x96, 0x53, 0x78, 0xCB, 0xE9, 0x18, 0xBF, 0x0F, 0x4B, 0xEE, 0xE1, 0xBD, 0x08, 0xFE, 0xCC, 0x66, 0x06, 0xD2, 0xF3, 0x97, 0x0C, 0x87, 0x4B, 0x0A, 0x09, 0xC4, 0x10, 0xE0, 0xC7, 0xD3, + 0xD6, 0x00, 0x4D, 0x93, 0xF0, 0x6F, 0xBC, 0x25, 0x8F, 0x96, 0x4A, 0x96, 0x19, 0xB2, 0xC6, 0xCA, 0x28, 0xA3, 0xA2, 0x52, 0x9B, 0xF4, 0x4F, 0xB9, 0xF2, 0x44, 0x38, 0x2C, 0xBE, 0xF9, 0x93, 0xC4, + 0x18, 0xA3, 0x88, 0x0F, 0x8D, 0x5F, 0xBA, 0x41, 0xF0, 0x58, 0x24, 0xF4, 0xF3, 0x3B, 0x24, 0xB8, 0x86, 0xD1, 0x15, 0xB8, 0x19, 0x81, 0x6C, 0x9B, 0x7D, 0xB5, 0x1F, 0x2A, 0xA0, 0xCC, 0x6B, 0x01, + 0xB6, 0xAB, 0x21, 0x1F, 0xAD, 0x55, 0x28, 0x4C, 0xDC, 0x04, 0x52, 0x47, 0x85, 0x90, 0x59, 0xBD, 0x36, 0x88, 0x7F, 0x3A, 0xE2, 0xB6, 0xCF, 0x7F, 0x87, 0xEC, 0x2D, 0xF3, 0xC8, 0x9D, 0x43, 0xD2, + 0x7E, 0x5E, 0x48, 0x88, 0xBA, 0xE6, 0x5B, 0x69, 0x24, 0xFA, 0x5D, 0xF0, 0xB2, 0xED, 0x44, 0xE3, 0xE3, 0x79, 0x4B, 0x68, 0x90, 0xF9, 0x33, 0xF9, 0xFB, 0xA7, 0xA7, 0x89, 0xFC, 0x63, 0xCE, 0xB7, + 0x43, 0x60, 0xD4, 0xAC, 0x9C, 0x64, 0xF1, 0x0C, 0xFC, 0x0A, 0xB3, 0x74, 0xC7, 0x12, 0xA3, 0xCC, 0x6C, 0x87, 0x6B, 0x22, 0xF6, 0xD9, 0xFE, 0xF1, 0xC3, 0x87, 0xBF, 0x6B, 0xDE, 0x75, 0x79, 0x2A, + 0xF9, 0x09, 0x4E, 0xC1, 0x7E, 0xB8, 0xB5, 0x5D, 0x35, 0x5F, 0xF0, 0xAE, 0x9D, 0x62, 0x11, 0x1A, 0xD8, 0xA3, 0xCB, 0xA4, 0xF5, 0x66, 0x3D, 0x94, 0xA3, 0x8A, 0x43, 0xE3, 0x52, 0x97, 0x9D, 0xB3, + 0xDF, 0xDF, 0x32, 0x98, 0x85, 0x34, 0xCD, 0x45, 0xFD, 0x43, 0x6E, 0x69, 0x9C, 0x46, 0x7F, 0x6D, 0xDD, 0x50, 0x76, 0xB4, 0xE5, 0xF7, 0xF3, 0x82, 0xAF, 0x45, 0xD3, 0x17, 0x0F, 0x25, 0xB5, 0x41, + 0x50, 0xD6, 0x4D, 0x35, 0xA8, 0x18, 0x55, 0xF4, 0xB2, 0x2B, 0xAC, 0x9F, 0xA1, 0x7D, 0xEF, 0xAD, 0x73, 0xB1, 0x4B, 0x15, 0x84, 0x0E, 0x08, 0x70, 0xDA, 0xF5, 0xB9, 0x2A, 0x30, 0xD2, 0x37, 0xBF, + 0x0C, 0x08, 0xCB, 0x8C, 0x9E, 0xBD, 0x41, 0x59, 0xD3, 0xBB, 0x2D, 0x47, 0x4E, 0x3E, 0x10, 0x6C, 0xC4, 0x68, 0xE6, 0xA2, 0x43, 0x35, 0x12, 0x48, 0x10, 0xF4, 0x86, 0xA6, 0x47, 0x3C, 0x26, 0xA5, + 0xD7, 0x83, 0x26, 0x4F, 0xD8, 0xA3, 0x68, 0x5C, 0x09, 0xD4, 0xEF, 0x77, 0xBD, 0x9A, 0x9A, 0x5C, 0x0B, 0x57, 0x8C, 0x95, 0xE7, 0xCA, 0xA3, 0x4E, 0xCE, 0x46, 0xF8, 0x48, 0x37, 0x47, 0xEE, 0x58, + 0x4D, 0xBB, 0x2D, 0x97, 0x20, 0x76, 0xD7, 0x63, 0xB0, 0xB5, 0x50, 0xE2, 0xCA, 0xE8, 0x34, 0x9E, 0x06, 0x09, 0xF1, 0x4F, 0x0A, 0x8F, 0x51, 0x10, 0xCA, 0xA4, 0xCD, 0xAB, 0xDD, 0x44, 0x40, 0xAD, + 0x16, 0x9C, 0x2A, 0xBE, 0x86, 0xEE, 0x1C, 0x68, 0x0D, 0x6E, 0x94, 0x88, 0x29, 0x64, 0xD8, 0x70, 0xCF, 0xEF, 0x70, 0xA4, 0xF4, 0xC0, 0x4B, 0x49, 0xCC, 0x4A, 0x4F, 0xF6, 0xD4, 0xB9, 0xE3, 0x69, + 0x18, 0xC1, 0x8A, 0x6D, 0x5C, 0x4A, 0xF4, 0x7C, 0xCF, 0x09, 0xFF, 0x64, 0xC7, 0x7A, 0xE3, 0xBF, 0xBC, 0xFA, 0x50, 0x4E, 0x16, 0x9E, 0xAB, 0xB3, 0x06, 0x95, 0x1A, 0x28, 0xAF, 0xF2, 0xFA, 0xB7, + 0xA5, 0xBA, 0x47, 0x6F, 0x56, 0x50, 0xBC, 0x7D, 0xA1, 0x92, 0xD4, 0xB0, 0xEB, 0xFA, 0xAB, 0xAB, 0xE7, 0x72, 0xED, 0xE2, 0xA1, 0x07, 0x1D, 0x5C, 0x4F, 0xC3, 0x3C, 0x25, 0x25, 0xE4, 0x0D, 0x08, + 0x2F, 0xA9, 0x35, 0xBD, 0x32, 0xFF, 0x25, 0x06, 0xB3, 0xA1, 0x31, 0xE3, 0x15, 0x81, 0xB6, 0xC9, 0x44, 0xC2, 0x5F, 0x2D, 0x81, 0x75, 0x5C, 0x39, 0xD3, 0xBF, 0xC0, 0xC6, 0xDE, 0x93, 0xE3, 0x55, + 0x57, 0xAB, 0x1C, 0xF3, 0x47, 0x2B, 0x4A, 0x32, 0x98, 0x09, 0x86, 0xA3, 0x1F, 0x88, 0x28, 0x73, 0x52, 0x19, 0x38, 0xD8, 0xBF, 0xFE, 0x97, 0x36, 0x9F, 0xE2, 0x97, 0x46, 0xAC, 0xFC, 0x8F, 0x12, + 0xDE, 0xEE, 0x0E, 0x9A, 0xC3, 0xE1, 0x67, 0x60, 0x20, 0x22, 0x43, 0x43, 0x58, 0xF9, 0xDC, 0x33, 0xB2, 0xD4, 0x40, 0x8F, 0xD0, 0x89, 0x54, 0xF9, 0x74, 0x5A, 0x0B, 0xD6, 0x5B, 0xC7, 0x7E, 0xE8, + 0xBE, 0xA7, 0x1B, 0xFA, 0x76, 0x40, 0xC1, 0x35, 0xED, 0x19, 0xCC, 0x2F, 0x1C, 0x22, 0xE0, 0xD6, 0xB0, 0x2D, 0xA6, 0xDF, 0x24, 0xDB, 0x05, 0xA6, 0x48, 0x0D, 0xB4, 0x52, 0x27, 0xDC, 0xC9, 0x7A, + 0xDC, 0xEC, 0xB3, 0x91, 0x7F, 0x08, 0x6C, 0x6E, 0x98, 0x08, 0x3A, 0x21, 0x2D, 0x54, 0xDC, 0x4B, 0x81, 0x0F, 0x68, 0x9C, 0x4F, 0x98, 0x43, 0xD2, 0xFB, 0x9F, 0x57, 0x26, 0xB8, 0x76, 0x64, 0xCD, + 0x32, 0x2C, 0x28, 0xB6, 0xF1, 0xE0, 0x1F, 0xA9, 0x1A, 0xB3, 0x50, 0x2F, 0xAC, 0x01, 0xAF, 0xCF, 0x52, 0xC9, 0xB3, 0xD2, 0xAA, 0x20, 0xE1, 0xB3, 0x85, 0xEF, 0x47, 0x0C, 0xB3, 0x30, 0x78, 0x19, + 0x8B, 0x5C, 0x43, 0x95, 0xA0, 0x32, 0x9C, 0xB1, 0x0F, 0x9A, 0x4E, 0x96, 0xF4, 0x3E, 0x51, 0x16, 0x1F, 0xAA, 0xE1, 0x90, 0xEB, 0x8C, 0x39, 0x69, 0xCE, 0xC2, 0x97, 0x7B, 0x08, 0xF6, 0x8D, 0x24, + 0xEF, 0xCE, 0x56, 0x65, 0x11, 0xFE, 0xB6, 0x54, 0xCC, 0x5F, 0xA1, 0xFE, 0x67, 0x57, 0x1F, 0x58, 0xD8, 0x48, 0xBE, 0x7C, 0x56, 0x4A, 0xF5, 0x66, 0x39, 0x06, 0x39, 0xF8, 0x16, 0x92, 0xA7, 0xB7, + 0xC0, 0xF9, 0xF5, 0xAD, 0x85, 0xB8, 0x2F, 0x6A, 0x83, 0x2C, 0x9D, 0xA5, 0x2B, 0x6A, 0x47, 0xD2, 0x3F, 0x9E, 0xCF, 0xAD, 0x44, 0x99, 0x83, 0xC9, 0x39, 0x65, 0x46, 0x58, 0xB1, 0x0A, 0xDD, 0xC0, + 0xB4, 0xAA, 0xDB, 0xB7, 0xB8, 0x5E, 0xA6, 0x02, 0xDA, 0x76, 0x17, 0xD1, 0xB4, 0xA4, 0x5D, 0x86, 0xB8, 0xD0, 0x9D, 0x2C, 0x5A, 0x40, 0x2A, 0x67, 0x58, 0xE0, 0x6A, 0xAA, 0x15, 0x4A, 0xD0, 0x96, + 0x67, 0x8C, 0xBD, 0xD9, 0xCA, 0x6F, 0x5D, 0x92, 0xB0, 0xD7, 0x38, 0x50, 0x1E, 0x18, 0xC1, 0xDC, 0xD2, 0x68, 0xDE, 0x01, 0x12, 0x00, 0x59, 0x48, 0x2D, 0xFC, 0xD1, 0x2B, 0x9B, 0xF2, 0x6E, 0x1C, + 0xF3, 0xB0, 0x99, 0x70, 0xC4, 0x3C, 0xF5, 0x62, 0x0C, 0xA8, 0xD4, 0xE2, 0xFD, 0x31, 0xE5, 0xA8, 0x9E, 0xF8, 0xDD, 0x93, 0x17, 0xE6, 0xCF, 0x55, 0xB3, 0xFB, 0x19, 0xC0, 0x72, 0xE9, 0xD5, 0xDD, + 0xB9, 0x74, 0xEF, 0x60, 0x82, 0x71, 0x1E, 0x99, 0x15, 0xD3, 0x43, 0x4E, 0x7D, 0x34, 0xE7, 0xC3, 0x25, 0xA8, 0xD9, 0x2B, 0x66, 0xB0, 0x83, 0xDF, 0xD6, 0xCF, 0xD1, 0x62, 0xFD, 0x66, 0x65, 0xDF, + 0x9A, 0xBF, 0x18, 0x8F, 0x2D, 0xC5, 0x83, 0xFD, 0xFA, 0xBC, 0x99, 0x7D, 0x78, 0x70, 0xE9, 0x11, 0xD3, 0xC5, 0xEB, 0x5B, 0xDF, 0x80, 0xBA, 0x8D, 0xE6, 0xC4, 0x6C, 0x88, 0xE0, 0x49, 0xD3, 0x9E, + 0x2F, 0xA2, 0x96, 0xCB, 0xE0, 0x69, 0xCA, 0x69, 0x49, 0x4F, 0x89, 0x08, 0x87, 0x67, 0x9C, 0xB3, 0xB0, 0xE6, 0x04, 0x3D, 0x02, 0xB8, 0xF2, 0x4A, 0x3F, 0x14, 0x83, 0xC9, 0x47, 0x81, 0xB6, 0xB0, + 0x1A, 0xF8, 0x01, 0x60, 0x63, 0x99, 0xC3, 0xAC, 0x62, 0x60, 0x3D, 0x86, 0xF7, 0xD5, 0x29, 0x55, 0xC3, 0x12, 0x59, 0x58, 0xC0, 0x4D, 0x57, 0x2A, 0x34, 0x63, 0x4C, 0xD2, 0x36, 0x73, 0x58, 0xA8, + 0x6A, 0xD2, 0xB4, 0x81, 0xB3, 0x26, 0xF2, 0xF8, 0x9D, 0x4B, 0x4D, 0xC0, 0x94, 0xE9, 0x89, 0x18, 0xB5, 0xAE, 0xD8, 0xF4, 0xEB, 0xA4, 0x9C, 0x56, 0x17, 0x2B, 0x16, 0x51, 0xB6, 0x60, 0xB8, 0x70, + 0x47, 0xBA, 0x65, 0x2A, 0x64, 0x0C, 0xA7, 0xB0, 0x69, 0x97, 0x1F, 0xA2, 0xA6, 0x6C, 0x01, 0x95, 0x67, 0xC3, 0x8B, 0x7F, 0x5D, 0x26, 0x21, 0xE7, 0xCB, 0x4B, 0xAA, 0x41, 0x40, 0xEF, 0x5B, 0xB4, + 0x91, 0x96, 0x0D, 0x80, 0xF5, 0x01, 0x01, 0xA0, 0x04, 0xE0, 0x79, 0xF5, 0xB5, 0x1F, 0x39, 0x4B, 0x02, 0x9E, 0x3E, 0xBF, 0xBD, 0xFC, 0x33, 0x59, 0x4E, 0x95, 0xF6, 0xA3, 0x7B, 0xC4, 0xF6, 0xA3, + 0x29, 0xB5, 0xC1, 0xD8, 0xE0, 0x41, 0x45, 0x40, 0x3D, 0x33, 0xA5, 0xC7, 0x04, 0xB3, 0x43, 0x51, 0x82, 0x31, 0xB0, 0x86, 0x46, 0xE4, 0xDA, 0x9D, 0x5A, 0x4E, 0xCA, 0xBC, 0xF5, 0x0F, 0x2B, 0x39, + 0x21, 0xE8, 0x5A, 0x84, 0xC4, 0x09, 0xA1, 0xF6, 0x27, 0xEE, 0x0F, 0x6E, 0xB1, 0xB1, 0xB9, 0xA9, 0xFC, 0xCA, 0x9C, 0xBD, 0x65, 0xCE, 0xA9, 0x00, 0x88, 0x79, 0x7D, 0xF7, 0x51, 0x0B, 0x86, 0x1B, + 0x86, 0xCA, 0x4E, 0x99, 0x8A, 0xF0, 0x75, 0x94, 0x9B, 0x16, 0x7C, 0xBD, 0x66, 0xBC, 0xBE, 0x4C, 0x51, 0x30, 0x34, 0x7D, 0x87, 0x7C, 0xE5, 0xA8, 0x47, 0x9F, 0x4D, 0x56, 0xD3, 0x98, 0x14, 0x6C, + 0xE2, 0xF1, 0xA7, 0x85, 0x42, 0x8D, 0xDD, 0xED, 0xAD, 0x66, 0xAA, 0xB2, 0x87, 0xCA, 0xAE, 0x59, 0x14, 0x24, 0x35, 0x56, 0x1A, 0x40, 0x1B, 0x50, 0x93, 0x43, 0x92, 0xD4, 0x32, 0x9C, 0x3C, 0x21, + 0xAE, 0x48, 0x32, 0x86, 0x53, 0xE3, 0xAE, 0x57, 0x5E, 0x18, 0x1D, 0xB3, 0x89, 0xBE, 0x43, 0x97, 0x16, 0xF6, 0xE3, 0xF3, 0xE2, 0xDC, 0x61, 0xE4, 0xEC, 0xCF, 0xE5, 0x48, 0xAB, 0x7D, 0x71, 0x5E, + 0xAB, 0x49, 0xCF, 0xD7, 0x64, 0x1D, 0xC3, 0x7F, 0x5C, 0x0C, 0x0C, 0x34, 0x96, 0x5C, 0x06, 0xA1, 0x56, 0x70, 0x5F, 0x98, 0x69, 0x58, 0x79, 0x1A, 0x59, 0xCD, 0x5B, 0x48, 0x90, 0xD9, 0xA1, 0xB1, + 0xCF, 0x08, 0x54, 0x1A, 0x7A, 0x93, 0xD0, 0x65, 0xDC, 0xF3, 0xB9, 0xF6, 0xC5, 0x13, 0xC0, 0x27, 0x94, 0x37, 0xD4, 0xBD, 0xBE, 0x62, 0x71, 0x40, 0xD2, 0x94, 0x63, 0x26, 0x39, 0xB7, 0x46, 0x89, + 0x1C, 0xA9, 0x70, 0xDF, 0x6D, 0x73, 0x21, 0xF1, 0xA9, 0x13, 0xAD, 0x9B, 0xED, 0x3F, 0xE0, 0xBC, 0x02, 0xAF, 0xBB, 0x87, 0x20, 0xB7, 0x42, 0xEB, 0x40, 0x9E, 0xB8, 0x2C, 0x66, 0x96, 0x7F, 0x60, + 0xEB, 0xF4, 0xCE, 0xE2, 0x50, 0x8E, 0xF7, 0xF7, 0x03, 0x5B, 0x7F, 0xC7, 0xD9, 0x17, 0x8E, 0x73, 0xED, 0xA0, 0x52, 0x9B, 0xCC, 0x9E, 0xB2, 0x0B, 0x9C, 0xD7, 0x74, 0xC5, 0x64, 0x88, 0x2D, 0xD5, + 0x7C, 0xCF, 0xB5, 0x46, 0x63, 0xCF, 0xA8, 0x1B, 0x91, 0x4E, 0x14, 0xC4, 0xD7, 0xD7, 0x4B, 0xCE, 0x13, 0x9B, 0x7E, 0xC5, 0x3E, 0xA6, 0x1B, 0x0B, 0xF0, 0xDB, 0x61, 0xC7, 0x3A, 0x7A, 0x95, 0xF5, + 0x96, 0xE1, 0x28, 0xEC, 0xA7, 0xA8, 0xC9, 0xEB, 0x92, 0xC2, 0x94, 0x4E, 0xF5, 0x64, 0x94, 0x3E, 0xDA, 0xCF, 0xD4, 0x8A, 0x5A, 0x8B, 0xDC, 0x7D, 0x0F, 0xAB, 0xFA, 0xB6, 0xDA, 0xD3, 0xC5, 0xFE, + 0xEE, 0xB1, 0x39, 0x81, 0x8C, 0x85, 0x73, 0xA7, 0xBD, 0x75, 0x06, 0xB1, 0x8B, 0xFC, 0xE2, 0xBA, 0x15, 0x10, 0x5B, 0x7C, 0xEC, 0x83, 0x09, 0x6C, 0x8C, 0xAE, 0x99, 0xFB, 0xE5, 0xEA, 0x2C, 0x10, + 0xF1, 0xBC, 0xF3, 0xF1, 0x58, 0x26, 0xA0, 0xD8, 0xEC, 0xA9, 0x7C, 0x42, 0xBB, 0x17, 0xCB, 0x9B, 0xED, 0x21, 0x9A, 0x8C, 0xDA, 0x9A, 0x57, 0x62, 0x85, 0x7E, 0xFB, 0xA4, 0x3B, 0x7F, 0x34, 0x15, + 0x7A, 0xEB, 0x49, 0x2F, 0x81, 0xD2, 0xEA, 0x15, 0x6F, 0xF4, 0x99, 0x12, 0xA4, 0x04, 0x9B, 0xE9, 0x3E, 0x12, 0xA2, 0x26, 0x29, 0x5D, 0x8F, 0x68, 0x5C, 0x89, 0xBD, 0xA3, 0x83, 0x1E, 0xB7, 0x3B, + 0xE4, 0x65, 0x7D, 0xBE, 0x3B, 0x09, 0xC0, 0x9D, 0x1D, 0xAF, 0x94, 0x4C, 0x26, 0x64, 0xE9, 0xBD, 0xE9, 0x17, 0x41, 0x98, 0xFE, 0x3D, 0xBA, 0xE4, 0xDE, 0x09, 0x45, 0x22, 0x9E, 0xDD, 0xF5, 0x96, + 0x1B, 0x2F, 0x3D, 0x71, 0x9F, 0xAB, 0xAE, 0xB9, 0xBB, 0xD0, 0xD6, 0x3F, 0x6B, 0x74, 0xF1, 0x47, 0x70, 0x9C, 0xB2, 0xC5, 0xCD, 0xDD, 0x25, 0x35, 0x41, 0xA2, 0xD4, 0xDB, 0xFE, 0x2F, 0x61, 0x9F, + 0xB6, 0xC0, 0xD8, 0x0D, 0x1D, 0x3D, 0x84, 0x93, 0x98, 0xBD, 0xF1, 0xFB, 0xFE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0B, 0x0F, 0x16, 0x1D, 0x23, 0x2D, + }, + }, + { + .name = "Dilithium Round 3, Level 3 (6-5) KAT 0", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_65, + .rho_len = 32, + .rho = { + 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, 0x38, 0xD5, 0x06, 0xD8, 0x5B, 0xEF, + }, + .seed_len = 32, + .seed = { + 0x39, 0x4D, 0x16, 0x95, 0x05, 0x9D, 0xFF, 0x40, 0xAE, 0x25, 0x6C, 0x5D, 0x5E, 0xDA, 0xBF, 0xB6, 0x9F, 0x5F, 0x40, 0xF3, 0x7A, 0x58, 0x8F, 0x50, 0x53, 0x2C, 0xA4, 0x08, 0xA8, 0x16, 0x8A, 0xB1, + }, + .tr_len = 32, + .tr = { + 0xE6, 0x4F, 0x14, 0x64, 0x27, 0x54, 0x3D, 0x8C, 0x36, 0xB3, 0xB6, 0x52, 0x26, 0x76, 0x9A, 0x22, 0x91, 0x1A, 0x5A, 0x31, 0x3E, 0xAC, 0x17, 0xC4, 0xAB, 0xA2, 0x52, 0x84, 0x51, 0x4F, 0xC6, 0x13, + }, + .s1_len = 640, + .s1 = { + 0x35, 0x78, 0x08, 0x33, 0x02, 0x23, 0x16, 0x43, 0x37, 0x65, 0x80, 0x75, 0x78, 0x71, 0x45, 0x24, 0x81, 0x01, 0x73, 0x15, 0x44, 0x83, 0x65, 0x26, 0x41, 0x33, 0x30, 0x22, 0x30, 0x26, 0x14, 0x73, + 0x70, 0x52, 0x21, 0x07, 0x81, 0x26, 0x50, 0x61, 0x85, 0x85, 0x07, 0x75, 0x46, 0x18, 0x58, 0x05, 0x48, 0x53, 0x30, 0x18, 0x70, 0x66, 0x47, 0x51, 0x82, 0x67, 0x73, 0x77, 0x33, 0x50, 0x02, 0x70, + 0x31, 0x28, 0x78, 0x82, 0x15, 0x80, 0x71, 0x40, 0x26, 0x73, 0x43, 0x20, 0x61, 0x62, 0x50, 0x61, 0x73, 0x71, 0x01, 0x03, 0x11, 0x45, 0x36, 0x81, 0x52, 0x30, 0x24, 0x65, 0x03, 0x48, 0x14, 0x37, + 0x08, 0x37, 0x18, 0x25, 0x50, 0x84, 0x06, 0x08, 0x60, 0x17, 0x62, 0x58, 0x31, 0x31, 0x28, 0x27, 0x00, 0x17, 0x18, 0x48, 0x16, 0x67, 0x31, 0x78, 0x61, 0x07, 0x37, 0x23, 0x55, 0x74, 0x47, 0x15, + 0x10, 0x10, 0x11, 0x21, 0x10, 0x66, 0x27, 0x42, 0x12, 0x08, 0x35, 0x46, 0x22, 0x85, 0x13, 0x13, 0x88, 0x16, 0x48, 0x86, 0x83, 0x35, 0x10, 0x47, 0x60, 0x26, 0x11, 0x83, 0x15, 0x74, 0x25, 0x00, + 0x74, 0x24, 0x40, 0x64, 0x25, 0x15, 0x86, 0x13, 0x65, 0x61, 0x37, 0x77, 0x11, 0x84, 0x78, 0x05, 0x08, 0x62, 0x43, 0x70, 0x64, 0x06, 0x85, 0x27, 0x63, 0x11, 0x50, 0x13, 0x56, 0x23, 0x21, 0x68, + 0x41, 0x41, 0x77, 0x24, 0x08, 0x48, 0x30, 0x87, 0x85, 0x75, 0x43, 0x85, 0x08, 0x63, 0x68, 0x54, 0x26, 0x84, 0x50, 0x56, 0x84, 0x37, 0x02, 0x40, 0x07, 0x16, 0x17, 0x84, 0x54, 0x38, 0x00, 0x61, + 0x27, 0x05, 0x82, 0x62, 0x06, 0x76, 0x52, 0x11, 0x12, 0x14, 0x83, 0x88, 0x06, 0x78, 0x14, 0x75, 0x55, 0x02, 0x12, 0x22, 0x85, 0x52, 0x31, 0x08, 0x45, 0x03, 0x70, 0x13, 0x64, 0x31, 0x80, 0x05, + 0x37, 0x68, 0x37, 0x65, 0x02, 0x46, 0x53, 0x15, 0x07, 0x60, 0x06, 0x25, 0x33, 0x12, 0x51, 0x20, 0x05, 0x41, 0x60, 0x63, 0x24, 0x23, 0x52, 0x41, 0x50, 0x77, 0x31, 0x45, 0x70, 0x33, 0x47, 0x65, + 0x64, 0x31, 0x23, 0x18, 0x03, 0x33, 0x65, 0x16, 0x75, 0x87, 0x14, 0x13, 0x04, 0x11, 0x17, 0x15, 0x54, 0x68, 0x12, 0x60, 0x53, 0x73, 0x42, 0x38, 0x82, 0x43, 0x27, 0x83, 0x37, 0x12, 0x22, 0x81, + 0x74, 0x81, 0x81, 0x20, 0x13, 0x63, 0x27, 0x64, 0x75, 0x10, 0x28, 0x03, 0x22, 0x68, 0x65, 0x08, 0x76, 0x55, 0x35, 0x63, 0x33, 0x81, 0x04, 0x47, 0x48, 0x58, 0x54, 0x30, 0x12, 0x43, 0x18, 0x08, + 0x38, 0x64, 0x38, 0x53, 0x83, 0x08, 0x41, 0x27, 0x04, 0x64, 0x64, 0x63, 0x34, 0x64, 0x61, 0x06, 0x80, 0x70, 0x60, 0x23, 0x75, 0x51, 0x68, 0x25, 0x74, 0x11, 0x52, 0x88, 0x22, 0x01, 0x57, 0x78, + 0x58, 0x33, 0x31, 0x34, 0x31, 0x55, 0x82, 0x84, 0x03, 0x16, 0x36, 0x01, 0x06, 0x48, 0x14, 0x80, 0x46, 0x43, 0x68, 0x46, 0x17, 0x57, 0x21, 0x36, 0x31, 0x65, 0x74, 0x65, 0x22, 0x15, 0x17, 0x71, + 0x32, 0x05, 0x10, 0x66, 0x46, 0x83, 0x16, 0x46, 0x71, 0x47, 0x28, 0x31, 0x35, 0x55, 0x14, 0x73, 0x32, 0x81, 0x82, 0x60, 0x73, 0x15, 0x54, 0x36, 0x87, 0x08, 0x03, 0x28, 0x43, 0x26, 0x24, 0x16, + 0x05, 0x32, 0x05, 0x20, 0x23, 0x67, 0x72, 0x58, 0x28, 0x18, 0x10, 0x85, 0x42, 0x67, 0x85, 0x15, 0x52, 0x80, 0x00, 0x72, 0x82, 0x27, 0x18, 0x31, 0x12, 0x08, 0x68, 0x37, 0x72, 0x44, 0x42, 0x05, + 0x48, 0x64, 0x72, 0x05, 0x35, 0x08, 0x61, 0x73, 0x86, 0x27, 0x12, 0x46, 0x77, 0x51, 0x08, 0x52, 0x76, 0x33, 0x40, 0x37, 0x34, 0x32, 0x11, 0x54, 0x24, 0x06, 0x54, 0x02, 0x34, 0x50, 0x80, 0x04, + 0x17, 0x72, 0x84, 0x62, 0x73, 0x61, 0x68, 0x68, 0x07, 0x81, 0x52, 0x46, 0x71, 0x06, 0x82, 0x55, 0x45, 0x81, 0x63, 0x62, 0x76, 0x41, 0x80, 0x57, 0x12, 0x44, 0x25, 0x57, 0x08, 0x04, 0x51, 0x06, + 0x63, 0x61, 0x15, 0x85, 0x86, 0x30, 0x46, 0x52, 0x07, 0x05, 0x32, 0x75, 0x02, 0x18, 0x22, 0x42, 0x83, 0x71, 0x02, 0x38, 0x52, 0x75, 0x28, 0x44, 0x20, 0x33, 0x00, 0x17, 0x23, 0x11, 0x14, 0x02, + 0x15, 0x76, 0x88, 0x38, 0x47, 0x62, 0x31, 0x85, 0x13, 0x52, 0x52, 0x10, 0x84, 0x38, 0x25, 0x55, 0x56, 0x74, 0x11, 0x44, 0x54, 0x67, 0x27, 0x85, 0x46, 0x58, 0x61, 0x70, 0x43, 0x07, 0x58, 0x80, + 0x06, 0x84, 0x55, 0x13, 0x53, 0x47, 0x81, 0x38, 0x12, 0x08, 0x00, 0x84, 0x31, 0x56, 0x22, 0x14, 0x66, 0x03, 0x15, 0x60, 0x01, 0x63, 0x68, 0x56, 0x36, 0x73, 0x61, 0x80, 0x80, 0x04, 0x55, 0x54, + }, + .s2_len = 768, + .s2 = { + 0x33, 0x73, 0x12, 0x58, 0x40, 0x31, 0x14, 0x80, 0x42, 0x03, 0x67, 0x33, 0x01, 0x82, 0x71, 0x55, 0x60, 0x65, 0x60, 0x34, 0x40, 0x51, 0x44, 0x34, 0x55, 0x48, 0x51, 0x12, 0x23, 0x76, 0x45, 0x10, + 0x64, 0x33, 0x73, 0x25, 0x38, 0x23, 0x38, 0x06, 0x24, 0x51, 0x61, 0x70, 0x81, 0x54, 0x11, 0x67, 0x17, 0x32, 0x00, 0x85, 0x32, 0x60, 0x40, 0x43, 0x71, 0x06, 0x80, 0x37, 0x37, 0x60, 0x70, 0x86, + 0x40, 0x87, 0x00, 0x03, 0x52, 0x45, 0x71, 0x48, 0x26, 0x22, 0x03, 0x50, 0x53, 0x56, 0x66, 0x03, 0x72, 0x18, 0x01, 0x37, 0x10, 0x37, 0x10, 0x36, 0x52, 0x78, 0x43, 0x28, 0x24, 0x64, 0x23, 0x20, + 0x47, 0x64, 0x23, 0x84, 0x00, 0x00, 0x67, 0x43, 0x64, 0x56, 0x52, 0x26, 0x21, 0x76, 0x65, 0x21, 0x24, 0x13, 0x88, 0x73, 0x47, 0x65, 0x08, 0x43, 0x12, 0x17, 0x01, 0x64, 0x71, 0x46, 0x54, 0x03, + 0x87, 0x24, 0x41, 0x77, 0x74, 0x13, 0x76, 0x78, 0x55, 0x21, 0x64, 0x11, 0x17, 0x31, 0x60, 0x50, 0x48, 0x26, 0x04, 0x14, 0x84, 0x74, 0x66, 0x38, 0x03, 0x35, 0x15, 0x58, 0x01, 0x73, 0x51, 0x26, + 0x21, 0x33, 0x62, 0x22, 0x27, 0x10, 0x63, 0x45, 0x60, 0x16, 0x57, 0x20, 0x77, 0x85, 0x48, 0x32, 0x72, 0x48, 0x31, 0x56, 0x16, 0x78, 0x34, 0x56, 0x40, 0x57, 0x68, 0x67, 0x34, 0x58, 0x35, 0x25, + 0x35, 0x20, 0x81, 0x55, 0x65, 0x48, 0x10, 0x32, 0x05, 0x33, 0x40, 0x16, 0x60, 0x74, 0x23, 0x71, 0x50, 0x16, 0x32, 0x53, 0x34, 0x66, 0x72, 0x70, 0x81, 0x11, 0x18, 0x24, 0x37, 0x32, 0x13, 0x11, + 0x54, 0x42, 0x40, 0x82, 0x61, 0x37, 0x75, 0x04, 0x67, 0x10, 0x08, 0x02, 0x61, 0x38, 0x68, 0x50, 0x71, 0x28, 0x37, 0x52, 0x66, 0x72, 0x24, 0x23, 0x08, 0x02, 0x10, 0x05, 0x01, 0x55, 0x20, 0x48, + 0x37, 0x44, 0x37, 0x71, 0x16, 0x42, 0x01, 0x23, 0x16, 0x71, 0x07, 0x82, 0x38, 0x08, 0x07, 0x10, 0x11, 0x24, 0x68, 0x25, 0x82, 0x40, 0x18, 0x15, 0x85, 0x18, 0x74, 0x20, 0x85, 0x38, 0x25, 0x83, + 0x10, 0x66, 0x75, 0x13, 0x12, 0x52, 0x85, 0x27, 0x65, 0x25, 0x60, 0x31, 0x47, 0x81, 0x62, 0x13, 0x81, 0x53, 0x47, 0x04, 0x22, 0x61, 0x05, 0x71, 0x55, 0x67, 0x44, 0x68, 0x20, 0x05, 0x45, 0x50, + 0x51, 0x48, 0x41, 0x13, 0x03, 0x83, 0x02, 0x41, 0x47, 0x47, 0x15, 0x62, 0x72, 0x02, 0x16, 0x53, 0x21, 0x03, 0x03, 0x87, 0x36, 0x03, 0x48, 0x67, 0x51, 0x76, 0x65, 0x27, 0x21, 0x42, 0x17, 0x26, + 0x25, 0x76, 0x65, 0x36, 0x12, 0x11, 0x12, 0x16, 0x87, 0x48, 0x45, 0x40, 0x33, 0x42, 0x68, 0x35, 0x44, 0x40, 0x68, 0x13, 0x60, 0x50, 0x31, 0x08, 0x17, 0x43, 0x56, 0x75, 0x06, 0x34, 0x61, 0x84, + 0x75, 0x57, 0x58, 0x58, 0x65, 0x44, 0x84, 0x07, 0x62, 0x31, 0x86, 0x70, 0x34, 0x33, 0x67, 0x58, 0x66, 0x67, 0x73, 0x20, 0x75, 0x17, 0x10, 0x36, 0x05, 0x27, 0x37, 0x24, 0x12, 0x20, 0x17, 0x38, + 0x87, 0x54, 0x40, 0x32, 0x26, 0x30, 0x62, 0x13, 0x54, 0x18, 0x36, 0x81, 0x55, 0x77, 0x32, 0x00, 0x10, 0x03, 0x65, 0x18, 0x57, 0x41, 0x86, 0x02, 0x14, 0x44, 0x33, 0x41, 0x02, 0x37, 0x55, 0x63, + 0x58, 0x75, 0x02, 0x61, 0x88, 0x64, 0x18, 0x51, 0x76, 0x24, 0x15, 0x85, 0x07, 0x11, 0x80, 0x35, 0x41, 0x51, 0x57, 0x42, 0x42, 0x58, 0x54, 0x56, 0x35, 0x45, 0x15, 0x57, 0x07, 0x63, 0x86, 0x77, + 0x24, 0x00, 0x17, 0x67, 0x83, 0x86, 0x86, 0x25, 0x88, 0x17, 0x75, 0x08, 0x61, 0x23, 0x60, 0x60, 0x65, 0x07, 0x33, 0x35, 0x06, 0x60, 0x52, 0x75, 0x02, 0x47, 0x24, 0x33, 0x64, 0x51, 0x35, 0x45, + 0x52, 0x55, 0x41, 0x48, 0x60, 0x42, 0x16, 0x43, 0x15, 0x63, 0x33, 0x16, 0x55, 0x67, 0x60, 0x70, 0x34, 0x26, 0x77, 0x08, 0x07, 0x60, 0x55, 0x30, 0x63, 0x50, 0x13, 0x37, 0x70, 0x77, 0x01, 0x37, + 0x45, 0x72, 0x74, 0x51, 0x28, 0x72, 0x83, 0x64, 0x74, 0x77, 0x80, 0x27, 0x30, 0x36, 0x44, 0x23, 0x10, 0x55, 0x24, 0x15, 0x43, 0x11, 0x63, 0x14, 0x65, 0x33, 0x63, 0x12, 0x11, 0x84, 0x63, 0x12, + 0x63, 0x88, 0x37, 0x62, 0x67, 0x48, 0x35, 0x13, 0x86, 0x35, 0x17, 0x83, 0x12, 0x58, 0x14, 0x47, 0x88, 0x56, 0x08, 0x48, 0x01, 0x42, 0x71, 0x64, 0x77, 0x53, 0x64, 0x73, 0x54, 0x66, 0x05, 0x56, + 0x60, 0x52, 0x37, 0x00, 0x46, 0x40, 0x31, 0x10, 0x55, 0x50, 0x45, 0x36, 0x48, 0x42, 0x34, 0x06, 0x61, 0x11, 0x75, 0x52, 0x61, 0x58, 0x52, 0x15, 0x73, 0x57, 0x31, 0x56, 0x15, 0x87, 0x78, 0x74, + 0x45, 0x03, 0x87, 0x20, 0x54, 0x56, 0x11, 0x66, 0x22, 0x04, 0x46, 0x14, 0x14, 0x61, 0x83, 0x00, 0x06, 0x86, 0x64, 0x06, 0x00, 0x47, 0x37, 0x44, 0x22, 0x50, 0x56, 0x01, 0x04, 0x57, 0x73, 0x50, + 0x74, 0x87, 0x02, 0x66, 0x37, 0x48, 0x68, 0x48, 0x02, 0x63, 0x28, 0x52, 0x63, 0x58, 0x11, 0x30, 0x44, 0x28, 0x68, 0x32, 0x61, 0x10, 0x61, 0x88, 0x26, 0x07, 0x00, 0x73, 0x38, 0x62, 0x55, 0x27, + 0x15, 0x53, 0x45, 0x32, 0x14, 0x25, 0x73, 0x23, 0x12, 0x21, 0x87, 0x86, 0x55, 0x67, 0x25, 0x67, 0x46, 0x74, 0x72, 0x81, 0x44, 0x54, 0x64, 0x15, 0x77, 0x41, 0x07, 0x80, 0x60, 0x56, 0x13, 0x16, + 0x15, 0x40, 0x44, 0x63, 0x47, 0x53, 0x30, 0x77, 0x61, 0x62, 0x50, 0x13, 0x38, 0x41, 0x47, 0x42, 0x66, 0x70, 0x52, 0x06, 0x70, 0x81, 0x25, 0x43, 0x17, 0x77, 0x70, 0x15, 0x22, 0x21, 0x82, 0x50, + }, + .t0_len = 2496, + .t0 = { + 0x01, 0x31, 0x73, 0x16, 0x9D, 0xB8, 0x08, 0x6B, 0x12, 0x27, 0x01, 0x70, 0x6A, 0xE4, 0x9B, 0x99, 0x30, 0x5E, 0xE6, 0xD0, 0x16, 0xF1, 0x6F, 0x9F, 0xAC, 0xC1, 0xF8, 0x35, 0x29, 0x8B, 0x41, 0xE2, + 0x16, 0x64, 0x20, 0x60, 0x05, 0xCE, 0xB9, 0x81, 0xA3, 0x5F, 0x18, 0x65, 0x1C, 0xDB, 0x90, 0xE6, 0x8C, 0x1F, 0x95, 0x0B, 0x05, 0x9F, 0x73, 0xD6, 0xD3, 0x14, 0x3A, 0x1F, 0x47, 0xAA, 0x21, 0xD8, + 0x0A, 0x05, 0xFA, 0xF5, 0xD3, 0xA4, 0x0F, 0x67, 0x14, 0x8D, 0x3A, 0x89, 0xA9, 0xFD, 0xA8, 0x03, 0x64, 0xD5, 0x7C, 0x7B, 0x8F, 0x68, 0x05, 0x8A, 0x25, 0xD0, 0x84, 0x98, 0xD9, 0xA9, 0xC3, 0x78, + 0xC9, 0x81, 0x85, 0xDB, 0x13, 0x25, 0x91, 0x59, 0xCA, 0xC4, 0x76, 0x9C, 0x34, 0xA0, 0x80, 0x23, 0xA3, 0x38, 0x8C, 0x35, 0x05, 0x40, 0x6F, 0xB2, 0x1C, 0x69, 0xEE, 0xC1, 0x2D, 0xAC, 0x95, 0xA3, + 0xC9, 0xBA, 0x61, 0x18, 0x52, 0x37, 0xF0, 0xFF, 0x1E, 0x0E, 0x05, 0xF1, 0xA6, 0xF5, 0xA0, 0xC0, 0x90, 0x90, 0x10, 0x06, 0x65, 0xA1, 0xAD, 0x3A, 0xFB, 0x10, 0x76, 0x84, 0x7B, 0x23, 0x2E, 0xEE, + 0xA7, 0x84, 0x09, 0xBD, 0x90, 0x55, 0xDB, 0x57, 0xC1, 0xB3, 0x1E, 0x28, 0xA0, 0x1D, 0x09, 0x99, 0x90, 0x35, 0xBD, 0xFC, 0x65, 0x7A, 0x61, 0x04, 0x01, 0x03, 0xEC, 0xEB, 0xDC, 0x79, 0x34, 0x09, + 0x73, 0x37, 0x34, 0xD9, 0x34, 0x2C, 0xC5, 0xA0, 0x69, 0xE0, 0x70, 0xC2, 0x42, 0x1D, 0xDE, 0x11, 0xC4, 0x9E, 0x17, 0x2D, 0xBE, 0x7F, 0xEA, 0xF9, 0xDE, 0xDD, 0xFB, 0x3D, 0xA5, 0xDA, 0xA6, 0xB3, + 0xDD, 0x13, 0x20, 0x0B, 0x09, 0x04, 0x2E, 0x14, 0x4E, 0xEA, 0x95, 0x1B, 0x43, 0xDA, 0x48, 0x15, 0x3C, 0x1F, 0x1D, 0x5C, 0x07, 0xFC, 0xF4, 0x73, 0xFA, 0x7F, 0x32, 0x1E, 0x72, 0x53, 0x45, 0x77, + 0xC8, 0x95, 0x15, 0x1B, 0x46, 0xE4, 0x83, 0x31, 0xDD, 0xE6, 0x1D, 0xA4, 0x5F, 0x86, 0x09, 0xAC, 0x59, 0x58, 0x18, 0x14, 0x66, 0x6E, 0x16, 0x58, 0xB4, 0x91, 0x14, 0x52, 0x4B, 0xA3, 0x84, 0x0C, + 0x6B, 0xC5, 0x59, 0x65, 0x51, 0xAE, 0xF4, 0x24, 0x12, 0xC8, 0xAA, 0xCC, 0xDD, 0x8E, 0xF6, 0x9E, 0x46, 0x38, 0x0E, 0x6D, 0xEF, 0x60, 0xFD, 0x91, 0x22, 0x8B, 0x99, 0xCB, 0x51, 0x1D, 0x68, 0xEF, + 0x66, 0x31, 0x74, 0x8A, 0x05, 0x48, 0x08, 0x3A, 0x21, 0x54, 0x45, 0xEC, 0x54, 0x69, 0x34, 0x71, 0xA8, 0x31, 0x04, 0x2C, 0xF4, 0x1D, 0x09, 0xAF, 0x89, 0x81, 0x19, 0xB0, 0xFC, 0x64, 0x6E, 0x48, + 0x45, 0x39, 0xC8, 0xC3, 0x2D, 0x5D, 0xC2, 0x4F, 0x94, 0x39, 0xD3, 0x3E, 0xEE, 0xA0, 0x33, 0xA4, 0x08, 0x15, 0x50, 0xFD, 0xB0, 0xB0, 0x89, 0x23, 0xDB, 0xA5, 0xD4, 0x4A, 0x1A, 0x87, 0x6F, 0xE7, + 0xEE, 0x43, 0x20, 0xBF, 0x02, 0xF9, 0xBE, 0x26, 0xF4, 0x18, 0xF3, 0x09, 0xFA, 0x11, 0xFC, 0xD0, 0xC8, 0x64, 0xA7, 0xAA, 0x34, 0x11, 0x50, 0x83, 0xC1, 0xEA, 0x77, 0x53, 0x45, 0xAC, 0x05, 0x48, + 0xC8, 0x77, 0xC6, 0x85, 0xEA, 0x8C, 0x91, 0xB9, 0x24, 0xAF, 0x4F, 0x60, 0x7E, 0xF3, 0x7A, 0x02, 0x08, 0xE2, 0x13, 0x09, 0xAB, 0x6D, 0x0F, 0x2F, 0x8A, 0x4E, 0xAA, 0x04, 0x51, 0xFF, 0x4A, 0x47, + 0xE6, 0xF4, 0x82, 0x95, 0x8D, 0x81, 0xA1, 0x66, 0xA6, 0xA0, 0x8A, 0x6A, 0x10, 0xFC, 0x8F, 0x9A, 0xDA, 0x42, 0xB6, 0x4A, 0x12, 0xB9, 0x35, 0x7D, 0x59, 0x8A, 0x36, 0x64, 0xE9, 0xDF, 0x13, 0x75, + 0x5C, 0x10, 0xFF, 0xD7, 0x17, 0x7E, 0x59, 0x4D, 0xFC, 0xBC, 0xFB, 0x5D, 0x11, 0xB6, 0xAD, 0xB1, 0x60, 0x74, 0x45, 0x47, 0x9A, 0x5D, 0xB1, 0xAD, 0x8C, 0xA6, 0xD9, 0x15, 0xF8, 0x97, 0x95, 0xD2, + 0x40, 0xCB, 0xED, 0xFA, 0xD2, 0x53, 0x9D, 0x10, 0x51, 0x8E, 0x53, 0xCC, 0x45, 0x0D, 0x6F, 0xC5, 0x38, 0x5A, 0xD6, 0xD7, 0x6B, 0x78, 0x30, 0xF1, 0x38, 0x28, 0x12, 0x06, 0x45, 0xE3, 0xA0, 0xA5, + 0xDC, 0xDE, 0xAF, 0x15, 0xF1, 0x96, 0x8E, 0x64, 0xB3, 0xB1, 0xCE, 0xAF, 0x53, 0x6C, 0xAA, 0x29, 0x53, 0xD1, 0x61, 0xC7, 0x55, 0x28, 0xC3, 0xFA, 0x84, 0x93, 0xE0, 0xC1, 0x77, 0xAE, 0x80, 0x7C, + 0xED, 0x37, 0x64, 0x8A, 0x82, 0xC9, 0xBE, 0x8B, 0xA9, 0x70, 0x29, 0x6D, 0x54, 0x3F, 0x6F, 0xBD, 0x67, 0x24, 0xA9, 0x9A, 0x68, 0xD2, 0xF6, 0x8C, 0x1F, 0xD3, 0x33, 0xF9, 0xDE, 0xF8, 0x52, 0x6D, + 0xB7, 0x83, 0x64, 0x55, 0xB3, 0x13, 0xE6, 0xBC, 0x36, 0x61, 0x78, 0xC9, 0xC5, 0x77, 0x21, 0x60, 0x1E, 0xC0, 0x33, 0x50, 0x54, 0xF0, 0x67, 0xB7, 0x8E, 0x66, 0x3A, 0x05, 0x8D, 0xBD, 0xA1, 0xC1, + 0x2D, 0x80, 0xA3, 0x92, 0xF8, 0x9C, 0x0A, 0xD9, 0xE2, 0xA3, 0xB2, 0xEA, 0x17, 0xE9, 0xC9, 0xA3, 0xB1, 0x4D, 0x17, 0x68, 0x22, 0xEE, 0xAC, 0x5F, 0xB5, 0xFF, 0x7D, 0x4C, 0x87, 0xD7, 0x60, 0x80, + 0xD2, 0xD4, 0x2D, 0x9A, 0xA4, 0xC9, 0x51, 0xF4, 0xCA, 0xF1, 0x1A, 0x24, 0x4E, 0xDA, 0x71, 0x1D, 0x12, 0x0A, 0x2E, 0xA3, 0x21, 0xD1, 0x55, 0x1D, 0x86, 0xCA, 0x92, 0x65, 0xE9, 0xCD, 0x5F, 0xA9, + 0x59, 0x1D, 0x88, 0x0E, 0x40, 0x3B, 0x68, 0x44, 0xF0, 0x51, 0xDC, 0x04, 0x87, 0x99, 0x72, 0xC8, 0x63, 0xB9, 0x7C, 0x72, 0xB4, 0x09, 0xC1, 0x9D, 0x5E, 0xBE, 0xE8, 0xAB, 0x58, 0xC6, 0xE7, 0xB3, + 0x93, 0x8A, 0x68, 0xA9, 0xCA, 0xD7, 0x5D, 0x80, 0xC6, 0xFF, 0xC4, 0xF2, 0x22, 0x54, 0xFF, 0x44, 0x20, 0xC6, 0x06, 0xAD, 0x12, 0x0C, 0xC2, 0x03, 0x46, 0xA7, 0xE7, 0x32, 0x4E, 0x78, 0xC8, 0x62, + 0xE0, 0xDE, 0xE1, 0x61, 0xA6, 0x4F, 0x44, 0x91, 0x7D, 0xB0, 0xC3, 0x8C, 0x1F, 0x79, 0xC9, 0x69, 0x22, 0x0D, 0x20, 0x2F, 0x88, 0x02, 0xD0, 0xF9, 0xD7, 0xAB, 0xFB, 0x2D, 0xE4, 0x34, 0xB1, 0xC5, + 0x3D, 0xAB, 0xB5, 0x75, 0x75, 0xEE, 0xBB, 0xBF, 0x31, 0xCF, 0xB2, 0x92, 0x48, 0x72, 0xFA, 0x01, 0x47, 0x3B, 0x39, 0x76, 0xAE, 0xAD, 0xC9, 0x96, 0x99, 0xB1, 0x38, 0x20, 0xFA, 0x08, 0x68, 0xF2, + 0xC9, 0xFD, 0x0D, 0x35, 0x2E, 0x25, 0x93, 0x27, 0x3C, 0xD6, 0x21, 0xB1, 0x97, 0x4F, 0xFA, 0x61, 0x87, 0xFA, 0x05, 0xC4, 0x11, 0x8D, 0x45, 0x17, 0xC9, 0x34, 0x15, 0x1C, 0x1F, 0xA3, 0x4B, 0xEC, + 0x3E, 0xD3, 0x63, 0x95, 0x98, 0xCB, 0xA2, 0x4E, 0x28, 0x22, 0x9C, 0xE9, 0xFD, 0x3B, 0x1D, 0xB4, 0x96, 0x9C, 0x12, 0xEE, 0x49, 0xE1, 0x8B, 0x36, 0xCE, 0x2B, 0x91, 0x45, 0xAA, 0xC7, 0x54, 0x28, + 0xDF, 0xFA, 0x14, 0x53, 0x02, 0xF4, 0x1D, 0x9E, 0x33, 0x94, 0xF3, 0x8D, 0x3F, 0x3C, 0x03, 0x34, 0xC4, 0x77, 0x4F, 0x1E, 0x94, 0x29, 0x6D, 0xE3, 0x6D, 0xC6, 0xE4, 0x30, 0xE4, 0xC0, 0xA5, 0x37, + 0xE6, 0x8B, 0xDD, 0x41, 0xAF, 0x04, 0x21, 0x19, 0x3B, 0x16, 0xAB, 0x18, 0x91, 0xFA, 0x83, 0x6C, 0xBC, 0x36, 0x7B, 0x40, 0x37, 0x05, 0xAB, 0xA5, 0xD2, 0xF9, 0xF2, 0xA4, 0xC2, 0xF2, 0x75, 0xEC, + 0x01, 0x0B, 0x2E, 0xAB, 0x84, 0x09, 0x5A, 0x56, 0x9D, 0xBA, 0xE4, 0x45, 0x7C, 0xC2, 0xAC, 0x1C, 0xFE, 0xB1, 0xED, 0xA4, 0x3C, 0x3E, 0x28, 0x19, 0x27, 0x3C, 0x48, 0x7A, 0xCB, 0xEB, 0xFA, 0x0A, + 0x0E, 0xD1, 0xCC, 0x46, 0x67, 0xA6, 0xF5, 0x77, 0xF6, 0x2D, 0xFB, 0x1B, 0xC8, 0xFE, 0xAF, 0xD8, 0x6D, 0x90, 0x10, 0x8E, 0x16, 0xB8, 0xB0, 0xE6, 0xC2, 0x67, 0x86, 0x86, 0xC9, 0x28, 0xA6, 0x68, + 0xBB, 0x98, 0x57, 0xFF, 0xB2, 0x8D, 0xE9, 0x05, 0x45, 0xCD, 0x44, 0x37, 0xDD, 0x32, 0xCC, 0xCC, 0xC6, 0xED, 0x58, 0xFB, 0x46, 0xFB, 0xF8, 0x5E, 0x0A, 0xEC, 0x0C, 0x81, 0x4E, 0x53, 0x62, 0x45, + 0x25, 0x2B, 0x80, 0x29, 0xF0, 0xA2, 0xAB, 0x44, 0xB9, 0x02, 0x7A, 0x7E, 0x35, 0xA9, 0x41, 0xFA, 0x11, 0x3C, 0x8D, 0x82, 0x97, 0x4E, 0xA2, 0x2D, 0xF0, 0x2D, 0x84, 0xE5, 0x32, 0x8C, 0xEA, 0x83, + 0xD1, 0x2D, 0x39, 0x9C, 0x7F, 0x02, 0x59, 0x05, 0x5F, 0x4B, 0x3A, 0xD7, 0x07, 0xE7, 0xB3, 0xE5, 0x37, 0xB9, 0x3D, 0xEA, 0x1A, 0x06, 0x6B, 0xDC, 0x77, 0x5F, 0xC7, 0xD1, 0xA6, 0xF0, 0xFE, 0x29, + 0xDD, 0xAF, 0xA9, 0xA7, 0xDA, 0x63, 0x0A, 0x46, 0x7E, 0xF6, 0xCB, 0xF5, 0xCC, 0xDF, 0xFD, 0x79, 0xF1, 0xC8, 0xBB, 0x6B, 0xB3, 0x88, 0x20, 0x35, 0xC7, 0x3C, 0xDF, 0x7E, 0xCF, 0xFB, 0x53, 0xC7, + 0x12, 0xA7, 0xC7, 0xEA, 0xA5, 0x97, 0x65, 0xEF, 0xA9, 0x60, 0xBF, 0x21, 0xE2, 0x5A, 0x67, 0x03, 0xFB, 0x30, 0x4F, 0x07, 0x73, 0x9F, 0xEB, 0xC6, 0x3F, 0x49, 0x6B, 0x13, 0xCC, 0xAA, 0x07, 0x73, + 0x38, 0xA0, 0xB9, 0xA9, 0x76, 0xA9, 0xF0, 0xFC, 0x57, 0x42, 0xD8, 0x5C, 0x4A, 0xF4, 0x01, 0xA4, 0xCE, 0x34, 0x1B, 0x47, 0xBE, 0x25, 0x94, 0xFF, 0x7E, 0x30, 0x19, 0xA0, 0xE0, 0x64, 0x53, 0x5F, + 0x9D, 0x93, 0x95, 0xCC, 0x74, 0xA6, 0xA6, 0xF0, 0x0E, 0x0C, 0x4E, 0x35, 0x30, 0xA7, 0xFE, 0x93, 0x10, 0xCE, 0x30, 0xB6, 0x92, 0x2D, 0x04, 0xFD, 0xE0, 0xAA, 0x74, 0x9C, 0xC3, 0xFD, 0xED, 0xB4, + 0xD8, 0x70, 0x8C, 0x1F, 0x69, 0x68, 0xBB, 0xED, 0xDD, 0xD5, 0x83, 0x3B, 0x29, 0x9D, 0x79, 0xD6, 0x14, 0x28, 0x18, 0x00, 0x99, 0xB0, 0xA9, 0x46, 0xA5, 0xD7, 0x90, 0x85, 0xDF, 0x7F, 0x87, 0x2C, + 0xBD, 0xD2, 0x19, 0xE6, 0xB8, 0xEF, 0x8B, 0x8A, 0xB5, 0xC1, 0xA1, 0x49, 0xE6, 0xE1, 0x5E, 0xF2, 0x82, 0x86, 0x54, 0xFA, 0xBE, 0xC2, 0x49, 0xAF, 0xAA, 0xC4, 0xDC, 0x0B, 0x3B, 0x54, 0x23, 0x34, + 0x16, 0x2F, 0xB0, 0x98, 0x00, 0xB6, 0xC3, 0x6C, 0xC9, 0x0F, 0x2A, 0x10, 0x65, 0x58, 0xBA, 0xE2, 0x19, 0x8F, 0xA7, 0xD1, 0xE2, 0xD7, 0x30, 0xDE, 0x46, 0xE3, 0x55, 0xAE, 0xA9, 0x32, 0x48, 0xE5, + 0x3A, 0xB2, 0x1B, 0x51, 0x8E, 0xC9, 0x9D, 0x5F, 0x3B, 0x02, 0x11, 0x96, 0xA0, 0xF6, 0x14, 0xA4, 0x6B, 0x94, 0x75, 0x62, 0x12, 0x34, 0x73, 0x3A, 0x28, 0xA4, 0x65, 0xCC, 0x5A, 0x7F, 0xD4, 0x32, + 0xC3, 0x62, 0x58, 0x12, 0xAA, 0xBB, 0xB4, 0x2D, 0x2D, 0x9C, 0xBE, 0xF1, 0x6C, 0xBE, 0xD9, 0x36, 0x72, 0x02, 0xB0, 0x28, 0x94, 0xD0, 0x6B, 0xB8, 0x01, 0xBD, 0xA8, 0x47, 0x2B, 0x99, 0x18, 0xB7, + 0xD7, 0x24, 0xE3, 0x65, 0x57, 0xDB, 0xE6, 0xB7, 0x63, 0x3A, 0x5F, 0xD2, 0x2D, 0x0E, 0x33, 0x6E, 0x55, 0x57, 0xAF, 0xC0, 0x18, 0xC8, 0x12, 0xE9, 0xE6, 0xA3, 0x5B, 0xFD, 0x8C, 0x60, 0xAB, 0x38, + 0x2E, 0x14, 0xFF, 0x51, 0x14, 0x2B, 0x2D, 0x2C, 0x75, 0xA7, 0x67, 0xF3, 0x24, 0x13, 0xBA, 0x38, 0x48, 0x75, 0x58, 0xF9, 0x34, 0x5C, 0xBE, 0x6F, 0xD1, 0xD6, 0xB7, 0x8C, 0x2E, 0x62, 0x2F, 0x3B, + 0x97, 0x62, 0x30, 0xF9, 0x9D, 0x6C, 0xBA, 0xF0, 0xBB, 0xD1, 0x49, 0x49, 0x51, 0x0A, 0x52, 0x64, 0x4E, 0xF3, 0xF3, 0x07, 0x88, 0x65, 0x03, 0x7A, 0x1C, 0x10, 0xF4, 0x7B, 0x59, 0x54, 0x66, 0x99, + 0xE1, 0xBD, 0x53, 0x9C, 0x7D, 0xDC, 0xC0, 0x3F, 0x71, 0xA0, 0x15, 0x8E, 0xA9, 0xF0, 0x17, 0x8E, 0x18, 0x7B, 0xB6, 0xD4, 0x94, 0x40, 0xDF, 0x2B, 0x10, 0x63, 0x0F, 0xBE, 0x2F, 0xEB, 0x50, 0x97, + 0xE4, 0x7F, 0x28, 0x57, 0x11, 0xCA, 0x6F, 0x83, 0x5A, 0x10, 0xD3, 0xAA, 0x75, 0xC0, 0x3C, 0x41, 0x84, 0xC0, 0x3E, 0xF3, 0x07, 0x5D, 0x49, 0xDC, 0xB2, 0x17, 0x7A, 0xBD, 0x53, 0xAD, 0x73, 0x99, + 0xD2, 0x90, 0xEA, 0x69, 0x1D, 0x64, 0x73, 0x29, 0x05, 0x63, 0x40, 0xE8, 0xC8, 0x36, 0xE9, 0x75, 0x0F, 0xD8, 0x81, 0xDC, 0xE3, 0x09, 0xD3, 0x09, 0xA9, 0x5B, 0x82, 0x49, 0x2D, 0x4B, 0xDC, 0x15, + 0xEC, 0xF8, 0xC7, 0xF5, 0xD3, 0xB9, 0xDD, 0x27, 0x55, 0x48, 0x51, 0x2D, 0xB5, 0xEF, 0x80, 0xCD, 0x40, 0x9E, 0xD3, 0x2B, 0x51, 0x48, 0xB8, 0x2B, 0xF2, 0x40, 0xA7, 0xDC, 0x72, 0xA1, 0x85, 0x23, + 0xD8, 0x08, 0xB7, 0xA4, 0xF9, 0xE2, 0x54, 0x79, 0x9E, 0x17, 0x27, 0x8F, 0xA8, 0x8D, 0xAE, 0xBC, 0x94, 0x46, 0x32, 0xE8, 0x3F, 0x86, 0x09, 0xD6, 0x81, 0xAB, 0x46, 0x35, 0x13, 0x02, 0x3D, 0x67, + 0xCD, 0x51, 0xB1, 0x53, 0xF0, 0x96, 0x29, 0x12, 0xDD, 0x64, 0xAB, 0x8F, 0x65, 0x29, 0xDC, 0x22, 0xAA, 0x89, 0xE5, 0x72, 0xA7, 0xF8, 0x9C, 0xB9, 0x7A, 0x8F, 0x45, 0x09, 0x31, 0x9D, 0x22, 0x3B, + 0xB2, 0x99, 0x74, 0x95, 0x17, 0x16, 0xFD, 0x31, 0x77, 0x14, 0x0A, 0x31, 0xEA, 0x20, 0x04, 0x8B, 0xAF, 0x0F, 0xCA, 0x23, 0x0C, 0xEF, 0x21, 0x96, 0x7A, 0xBD, 0x83, 0x30, 0x9A, 0x4F, 0xF7, 0xE3, + 0x5E, 0x88, 0x78, 0x4D, 0xCA, 0x77, 0xAC, 0x07, 0x90, 0x20, 0xEC, 0x0C, 0xA6, 0xDD, 0xEF, 0xBC, 0xBB, 0x7E, 0x31, 0x73, 0x29, 0x31, 0x46, 0x65, 0xD7, 0xC5, 0x1F, 0x63, 0x1F, 0x68, 0x1B, 0x60, + 0x03, 0x64, 0xE4, 0x75, 0x74, 0xF2, 0x52, 0xBA, 0xD6, 0x39, 0x6B, 0x3F, 0x5B, 0x17, 0xAD, 0xC2, 0x20, 0x96, 0x6A, 0x93, 0xCE, 0x8F, 0x31, 0x5A, 0x2F, 0x83, 0x06, 0x8D, 0x2E, 0xA0, 0x69, 0x52, + 0xE6, 0xEB, 0xD8, 0x02, 0x47, 0x3A, 0x22, 0x64, 0xEF, 0xA4, 0x05, 0xB3, 0xE4, 0x91, 0xBE, 0x77, 0x6C, 0x50, 0x40, 0x6E, 0x11, 0x50, 0xC5, 0x6B, 0x89, 0x4C, 0xF8, 0x64, 0x54, 0x6B, 0x0C, 0x7A, + 0x65, 0xE3, 0xF1, 0xA2, 0xBE, 0xFE, 0xF2, 0xA9, 0x99, 0x0B, 0xAF, 0xE7, 0x0B, 0x6C, 0xA9, 0xF9, 0x1A, 0x8F, 0x3D, 0xD2, 0x13, 0x07, 0xA3, 0x9A, 0x2A, 0xFB, 0xDF, 0xBD, 0xE9, 0xB7, 0xCA, 0x3D, + 0x78, 0x28, 0xB1, 0x3F, 0x49, 0xDE, 0xCD, 0x72, 0x9C, 0x00, 0x39, 0xE9, 0x4E, 0xBB, 0x7B, 0x4B, 0xDA, 0x09, 0xB3, 0x50, 0x55, 0x29, 0xA1, 0x2C, 0xB1, 0xE2, 0xFD, 0x79, 0xB9, 0xE5, 0x08, 0x7C, + 0xD7, 0xC3, 0xBC, 0x05, 0xF7, 0xCF, 0xFB, 0xBA, 0x93, 0x2A, 0x7B, 0xFF, 0x8E, 0x67, 0x55, 0x5F, 0xEE, 0x03, 0x04, 0xD8, 0x90, 0x31, 0x3F, 0x86, 0xE1, 0x89, 0x25, 0x69, 0xE2, 0xD6, 0xF1, 0x4A, + 0x89, 0x93, 0x87, 0x17, 0xAA, 0xA3, 0xA3, 0x2A, 0xD1, 0x16, 0x71, 0x50, 0x29, 0x9C, 0x21, 0x82, 0x0A, 0xBD, 0x70, 0xFF, 0x90, 0x2B, 0x00, 0x4C, 0x6D, 0xE9, 0x1C, 0x1C, 0x0B, 0x40, 0x70, 0x64, + 0x42, 0xAF, 0x53, 0x1E, 0xC4, 0x90, 0xB0, 0x12, 0x75, 0x0B, 0xCB, 0x48, 0x77, 0x93, 0x5A, 0x7E, 0x54, 0x03, 0x17, 0x02, 0xBB, 0x98, 0x8E, 0xB3, 0xF9, 0x29, 0x14, 0xCD, 0xBD, 0x42, 0x97, 0x9A, + 0xD7, 0xD2, 0x7B, 0x22, 0x33, 0xEC, 0x12, 0x79, 0xD0, 0x54, 0x93, 0xB1, 0x2D, 0x3F, 0x5F, 0xBB, 0x77, 0x57, 0x53, 0x60, 0x21, 0xB5, 0xF4, 0xCD, 0x93, 0x2B, 0x48, 0x0E, 0x40, 0xCB, 0xAE, 0x50, + 0xD2, 0x32, 0xE0, 0xA2, 0xEF, 0xFE, 0x0E, 0x8C, 0xB5, 0x88, 0x08, 0x66, 0x91, 0x99, 0xF0, 0x83, 0x08, 0x72, 0xF3, 0x69, 0x73, 0x86, 0x82, 0xF8, 0x46, 0xF6, 0xDE, 0xAD, 0x09, 0x5B, 0xFF, 0xCD, + 0x67, 0x0A, 0x4A, 0x9C, 0xD1, 0x42, 0x39, 0x6C, 0x58, 0x50, 0x6E, 0xA7, 0xA6, 0x8B, 0x21, 0xAB, 0xDC, 0xC1, 0x9C, 0xCC, 0x06, 0xF6, 0xDA, 0x55, 0xC8, 0x85, 0xA8, 0x55, 0xC4, 0x56, 0x68, 0x0C, + 0xD4, 0x47, 0x7B, 0xCA, 0x2B, 0xBA, 0x91, 0x53, 0xDC, 0xAE, 0xE6, 0x82, 0x65, 0x5B, 0x74, 0xEC, 0xA6, 0xF7, 0xE4, 0x4C, 0x3B, 0xFE, 0x1E, 0x2D, 0x45, 0x74, 0x91, 0xED, 0x1B, 0xC6, 0x4E, 0x1C, + 0xF6, 0xCE, 0x18, 0xCF, 0x44, 0xA0, 0x16, 0x6D, 0x1B, 0x24, 0x44, 0x80, 0x88, 0x2C, 0x1B, 0x35, 0xCE, 0xA7, 0x03, 0x15, 0x8E, 0x18, 0xC7, 0xEC, 0x6E, 0x0C, 0xF8, 0x27, 0xD5, 0x50, 0x4A, 0x45, + 0xAE, 0x61, 0x15, 0x23, 0x09, 0xBC, 0x8A, 0x18, 0xA5, 0x2C, 0x0E, 0x76, 0x99, 0xA8, 0x7C, 0x4E, 0x31, 0xC6, 0x91, 0x1A, 0x83, 0x05, 0x35, 0x15, 0x55, 0xB2, 0x97, 0x1C, 0x94, 0x60, 0x2B, 0x70, + 0xE6, 0x70, 0xAA, 0x30, 0xB9, 0x07, 0x34, 0xEC, 0x1D, 0xAA, 0xD0, 0x3A, 0x30, 0xA9, 0x6F, 0x58, 0x47, 0xC5, 0xC3, 0xF7, 0x97, 0x3C, 0xF4, 0x57, 0x2D, 0x16, 0x6C, 0x51, 0xD1, 0xE9, 0x4A, 0x50, + 0xA4, 0xC1, 0xC8, 0x94, 0xA2, 0x05, 0xF8, 0xEC, 0xB3, 0x4E, 0x80, 0xF8, 0x4C, 0xA8, 0xDC, 0x31, 0xA4, 0x29, 0xD5, 0x60, 0x05, 0x96, 0x17, 0x9D, 0x10, 0x93, 0xE2, 0xA3, 0x89, 0xCC, 0xFE, 0x9C, + 0x04, 0x02, 0xEE, 0x49, 0x55, 0x17, 0x10, 0xFF, 0xC2, 0x5B, 0xDB, 0xE4, 0x78, 0xF3, 0x9F, 0x20, 0x63, 0xF3, 0x1F, 0x75, 0xD7, 0x43, 0x2E, 0xCA, 0x1C, 0x59, 0xEB, 0xD8, 0xF4, 0x6D, 0x86, 0xA0, + 0x92, 0xDB, 0x12, 0xF8, 0x10, 0xFA, 0x91, 0x1C, 0x20, 0xD4, 0xCC, 0x1E, 0x42, 0x5C, 0x54, 0x3D, 0xC6, 0x45, 0x77, 0xE4, 0x4D, 0x84, 0xF4, 0x22, 0xD9, 0x66, 0x1E, 0x3D, 0x35, 0x92, 0x13, 0x50, + 0xD6, 0xF7, 0x09, 0x9C, 0x54, 0x25, 0xE5, 0x09, 0xE1, 0x45, 0x8A, 0x05, 0x00, 0xAE, 0x5E, 0xB4, 0xCC, 0x6B, 0xB5, 0x06, 0x26, 0xD0, 0x13, 0x0F, 0x09, 0x36, 0x17, 0x17, 0xA9, 0x59, 0x19, 0xAE, + 0xD3, 0x55, 0x92, 0xFA, 0x4A, 0xBE, 0x7B, 0x2B, 0xD4, 0xF9, 0x99, 0x42, 0x21, 0x51, 0xE6, 0x3D, 0x4E, 0xD0, 0x0C, 0xC7, 0x51, 0xA5, 0x86, 0x79, 0x77, 0xF1, 0x5E, 0x48, 0x2E, 0xFA, 0x01, 0xE5, + 0xCC, 0xC4, 0x40, 0x64, 0xF5, 0xB9, 0xFF, 0xE2, 0x9A, 0xFF, 0xE6, 0x26, 0xC4, 0xD5, 0x17, 0x0A, 0xDA, 0x1D, 0xF0, 0x27, 0xAB, 0x41, 0x79, 0x60, 0x8C, 0x40, 0x93, 0xCC, 0xE2, 0xC4, 0x09, 0x30, + 0x8C, 0xD8, 0x98, 0x37, 0x1A, 0x49, 0xFB, 0xEA, 0x2A, 0x2F, 0x2B, 0xA1, 0x3B, 0xDE, 0xBA, 0xC1, 0xF4, 0x15, 0x9F, 0x4B, 0x03, 0x68, 0xFB, 0x21, 0xD7, 0x0A, 0x9D, 0x79, 0x31, 0xD7, 0xEF, 0xF9, + 0x34, 0xE6, 0xC5, 0x44, 0xE1, 0x3B, 0x7B, 0x73, 0xD4, 0x65, 0x57, 0x6C, 0x6E, 0x81, 0xFD, 0x6D, 0x5F, 0xD9, 0x43, 0x93, 0xE8, 0x02, 0x42, 0xF9, 0x42, 0x0A, 0xCC, 0x0E, 0xD3, 0x53, 0xEF, 0x18, + 0xCA, 0x07, 0x0F, 0x5E, 0x9A, 0x28, 0x5A, 0xC4, 0xBC, 0xBA, 0xB1, 0x9A, 0x38, 0x35, 0x6F, 0x55, 0x7B, 0x07, 0x0E, 0x17, 0xAE, 0x5C, 0xF1, 0xF1, 0xBE, 0xD4, 0x26, 0x01, 0xE8, 0x9C, 0x8C, 0x4C, + }, + .t1_len = 1920, + .t1 = { + 0xD9, 0xFD, 0xE3, 0xA4, 0x96, 0xF7, 0x58, 0x19, 0xF0, 0xA2, 0x0D, 0x04, 0x41, 0xDC, 0x78, 0x30, 0xB4, 0xAA, 0x1C, 0xB8, 0xEC, 0xFC, 0x91, 0xBA, 0x0E, 0xEC, 0x3A, 0xFB, 0x67, 0x44, 0xE4, 0x77, + 0xB4, 0xE6, 0xEC, 0x3F, 0xDA, 0xE7, 0x50, 0x48, 0xFF, 0xEB, 0xAA, 0xBE, 0xA8, 0xE8, 0x22, 0x11, 0x7D, 0x57, 0x87, 0xF7, 0x90, 0x70, 0xEA, 0x88, 0x28, 0x7C, 0xE3, 0xCD, 0x50, 0x11, 0xFD, 0x8D, + 0x93, 0xAB, 0x7E, 0x8B, 0x51, 0xF2, 0x61, 0x16, 0xBF, 0x9B, 0x6D, 0x21, 0xC0, 0x3F, 0x88, 0xBF, 0xEC, 0x48, 0x88, 0x76, 0xF4, 0xD0, 0x75, 0xA1, 0x42, 0xD4, 0xE7, 0x84, 0xD7, 0x34, 0x40, 0x75, + 0x11, 0xF9, 0x92, 0x06, 0x93, 0x53, 0xF1, 0xDB, 0x67, 0xAC, 0xF7, 0x30, 0x34, 0xA4, 0x68, 0xA1, 0x18, 0x58, 0x80, 0x62, 0x11, 0x1D, 0x32, 0x0E, 0x00, 0xBC, 0xFF, 0x6D, 0xC6, 0x35, 0x73, 0xFC, + 0xED, 0x1E, 0x96, 0xAA, 0xEB, 0xA6, 0x45, 0x2E, 0x3C, 0x7A, 0xCD, 0x19, 0x18, 0x1F, 0x9B, 0x81, 0x4B, 0xA1, 0x9D, 0x39, 0xB4, 0xBA, 0xB5, 0x49, 0x6D, 0xC0, 0x55, 0x42, 0x6E, 0x7E, 0xA4, 0x61, + 0xAF, 0x55, 0xD5, 0xB9, 0xFE, 0x97, 0xF9, 0xDF, 0x7E, 0x25, 0x32, 0x03, 0xC1, 0xF9, 0xE1, 0x52, 0xE9, 0x6D, 0x75, 0xF9, 0xD9, 0xA8, 0x4F, 0x5C, 0x26, 0x3E, 0xC8, 0xC2, 0x50, 0x44, 0x0A, 0xDC, + 0x98, 0x6F, 0x4E, 0x36, 0x41, 0x4C, 0x70, 0x3B, 0x3E, 0x05, 0x42, 0x6B, 0x28, 0xB7, 0x06, 0x59, 0x50, 0xDA, 0x6D, 0x0E, 0x0B, 0x2C, 0x60, 0xAC, 0x36, 0x72, 0xDB, 0x6F, 0x3C, 0x78, 0x44, 0x7D, + 0xB7, 0xC2, 0x09, 0x15, 0x77, 0x0E, 0xA6, 0xFC, 0xE8, 0x1D, 0xAB, 0x53, 0x39, 0xC1, 0xD5, 0xAF, 0x82, 0xA5, 0xD3, 0x32, 0x40, 0x99, 0xDF, 0x56, 0x51, 0x6A, 0x07, 0xDB, 0x7C, 0x0F, 0xC6, 0x43, + 0x83, 0x80, 0x5C, 0x65, 0xF2, 0xB0, 0x2F, 0xBC, 0xFC, 0xE6, 0x3E, 0x93, 0xC4, 0xBF, 0x09, 0x40, 0x9F, 0x9F, 0x0F, 0x77, 0xE7, 0x3D, 0xA3, 0xB0, 0x01, 0x9F, 0x20, 0x57, 0xE4, 0xCD, 0x7C, 0xFF, + 0x0E, 0x57, 0x45, 0xEF, 0x18, 0xC3, 0xFD, 0x76, 0x6E, 0x01, 0x74, 0x7A, 0x64, 0xD4, 0x15, 0xFC, 0x97, 0x89, 0xAB, 0xFA, 0x62, 0x28, 0x4E, 0x11, 0xC7, 0xFF, 0x05, 0xD0, 0x54, 0x8D, 0x97, 0x3F, + 0x67, 0x95, 0x59, 0xA6, 0xA3, 0xAA, 0xD7, 0x7E, 0xD5, 0x13, 0x2D, 0x01, 0x50, 0xC0, 0x14, 0xC3, 0xEC, 0x3A, 0x39, 0x5F, 0x01, 0x7E, 0x7A, 0xCF, 0xE3, 0xEA, 0xBF, 0xCA, 0x44, 0x91, 0x0C, 0xA0, + 0x6F, 0xF3, 0x35, 0x42, 0xEC, 0xCE, 0x62, 0x41, 0x97, 0x47, 0x42, 0x35, 0x7D, 0x37, 0xF5, 0xC2, 0x84, 0xBF, 0x0F, 0xE1, 0xA7, 0x4B, 0x50, 0xC0, 0x73, 0x55, 0x13, 0x72, 0x13, 0x3A, 0xF2, 0xDD, + 0x41, 0xE2, 0x1B, 0xAF, 0xC9, 0xC5, 0x90, 0xEE, 0x6E, 0xBC, 0x4A, 0xCE, 0x73, 0x1E, 0xF5, 0x66, 0x15, 0x6C, 0xA0, 0x37, 0x55, 0xDC, 0x49, 0x3C, 0x13, 0x70, 0x28, 0xAF, 0x3B, 0x3D, 0xE5, 0xB0, + 0x0B, 0xD6, 0xCB, 0x3D, 0x9A, 0x87, 0xD0, 0x15, 0x1F, 0x88, 0x7C, 0x67, 0x68, 0xBC, 0x6C, 0xA0, 0x2A, 0x94, 0xFB, 0x20, 0x86, 0x55, 0x1A, 0x0F, 0x89, 0xBA, 0x26, 0x15, 0x4E, 0x9D, 0x45, 0x06, + 0xAD, 0x9F, 0xAF, 0x39, 0xF5, 0x72, 0x3E, 0x23, 0x4E, 0x06, 0xCF, 0xDE, 0xD6, 0x9D, 0x4E, 0xE4, 0x14, 0x6B, 0x73, 0xE5, 0xDC, 0x1E, 0x41, 0x52, 0xA2, 0xA3, 0x15, 0x9D, 0x73, 0xDB, 0xC8, 0x33, + 0xD3, 0xD4, 0x17, 0xCD, 0x5C, 0xF7, 0xFB, 0x3D, 0xC7, 0x74, 0x5C, 0xEE, 0xD4, 0xDC, 0x0F, 0x5B, 0x1C, 0x6D, 0x6B, 0x69, 0xC1, 0x76, 0x41, 0x57, 0xEA, 0x43, 0xDF, 0x9D, 0xBB, 0x44, 0x2E, 0xFA, + 0x39, 0xD1, 0xD0, 0x16, 0x2E, 0x87, 0xC2, 0xD3, 0x0C, 0x50, 0x12, 0xFD, 0x16, 0xD8, 0x69, 0xC8, 0xA1, 0xFC, 0xBB, 0x45, 0xED, 0xCC, 0x8E, 0x18, 0x13, 0xB2, 0xB1, 0x90, 0xA9, 0x61, 0xF9, 0xFC, + 0x86, 0x59, 0x1D, 0x3A, 0xBC, 0x53, 0x88, 0xAF, 0x67, 0x8F, 0xF0, 0x3D, 0xA7, 0x8B, 0x7C, 0xC0, 0xF6, 0x18, 0x57, 0x21, 0xC0, 0xDF, 0x33, 0xCC, 0x90, 0x64, 0x35, 0x22, 0x5D, 0xF2, 0x61, 0x10, + 0x02, 0xDF, 0x12, 0x0E, 0x83, 0x56, 0x65, 0x32, 0x29, 0x2D, 0xEA, 0x3D, 0x8A, 0xCD, 0x10, 0x9A, 0x0D, 0xFF, 0xAB, 0x3B, 0x0B, 0x43, 0x01, 0x27, 0x96, 0xDB, 0x5B, 0x50, 0x68, 0x3F, 0xB4, 0xC2, + 0xD2, 0x50, 0xDA, 0xB7, 0x6A, 0xAE, 0x35, 0xA4, 0x8E, 0x8C, 0x8D, 0x4A, 0x5C, 0xC1, 0x54, 0x75, 0x97, 0x45, 0xF0, 0xA1, 0x23, 0x0F, 0x6C, 0xA9, 0xDD, 0x9C, 0x99, 0xE2, 0xF8, 0x0E, 0xDC, 0x83, + 0x30, 0x4C, 0xE0, 0x1E, 0x98, 0xF6, 0xC9, 0x48, 0x95, 0x29, 0xA8, 0x22, 0xF9, 0x00, 0x33, 0xC2, 0x28, 0x31, 0x5E, 0xB2, 0xFC, 0xC8, 0xDB, 0xA3, 0x82, 0xED, 0x43, 0x01, 0xE0, 0x76, 0x07, 0xA5, + 0xB0, 0x76, 0xC7, 0x25, 0xF1, 0x24, 0x99, 0x4F, 0x18, 0xA9, 0x97, 0xD2, 0xC5, 0xBB, 0xF9, 0xA3, 0x24, 0x60, 0x52, 0x65, 0x10, 0x8A, 0xCB, 0xF4, 0x61, 0x0F, 0xA1, 0xC3, 0x37, 0x44, 0x08, 0x85, + 0x0A, 0x08, 0x64, 0xE2, 0xB6, 0x10, 0x17, 0xEB, 0xEC, 0x1F, 0xBA, 0xB8, 0x9D, 0xE3, 0xAB, 0x1B, 0x93, 0xCE, 0x49, 0x18, 0xB9, 0xE2, 0xC9, 0xE3, 0xFE, 0x45, 0x67, 0x58, 0x06, 0x2A, 0x9F, 0x88, + 0x2B, 0x28, 0x33, 0x18, 0x27, 0x1F, 0x4B, 0x95, 0x52, 0xFC, 0xF3, 0x26, 0x24, 0xA9, 0xFD, 0xAA, 0x44, 0xC6, 0x5C, 0x60, 0xE2, 0xB3, 0x64, 0x8B, 0xEF, 0x1F, 0x17, 0xD0, 0xB7, 0xC7, 0x48, 0x69, + 0xEE, 0x0B, 0x53, 0xC4, 0xA6, 0x2A, 0x24, 0x84, 0x5D, 0xCE, 0xA5, 0xBC, 0xBF, 0x93, 0xB9, 0x2E, 0x4C, 0x26, 0x64, 0x85, 0x84, 0xE3, 0x34, 0x79, 0x28, 0x2E, 0x6C, 0x8B, 0x1D, 0x8F, 0xE2, 0x11, + 0x81, 0xBD, 0x9C, 0xF7, 0x5F, 0x8A, 0x96, 0x17, 0x24, 0xD4, 0xC4, 0x30, 0x97, 0x79, 0xF1, 0xF1, 0xB7, 0x75, 0xD2, 0x54, 0xF7, 0x0B, 0xD1, 0x76, 0x9C, 0xC7, 0xC0, 0xED, 0xD2, 0xA9, 0x5F, 0xE5, + 0xC9, 0xD8, 0x4B, 0x16, 0xF7, 0xC5, 0x4D, 0x85, 0xCC, 0xE4, 0xC8, 0xA1, 0x82, 0x81, 0x08, 0x09, 0xED, 0x81, 0xE9, 0x7D, 0x07, 0x48, 0x84, 0xEE, 0xDF, 0x40, 0x1C, 0xCA, 0xCD, 0xAE, 0xAD, 0x82, + 0xC1, 0x4D, 0x06, 0xB6, 0x8A, 0xEA, 0x6C, 0xE1, 0x4B, 0x86, 0x1B, 0x0C, 0xFD, 0x16, 0x09, 0x0C, 0xBB, 0xF4, 0x69, 0xC5, 0xE0, 0x84, 0x31, 0x4C, 0x0D, 0x8D, 0x39, 0x60, 0xEA, 0x06, 0xA3, 0x42, + 0x6D, 0x8B, 0x3F, 0xE7, 0x62, 0xE0, 0x0D, 0x09, 0xBD, 0xA3, 0x74, 0xF3, 0xAE, 0x2C, 0xBE, 0xDE, 0x28, 0x38, 0xFF, 0x89, 0xD8, 0x1D, 0xEB, 0x30, 0x13, 0x09, 0x0E, 0x44, 0x19, 0x9A, 0xED, 0x60, + 0x49, 0x63, 0xEA, 0xF9, 0x19, 0x91, 0x4C, 0xE0, 0x4F, 0x20, 0x7A, 0xC8, 0x2C, 0xD4, 0x35, 0x1F, 0xEF, 0x7B, 0x2D, 0x94, 0x39, 0x30, 0x66, 0xFE, 0x4D, 0x44, 0xE3, 0xCC, 0x59, 0x52, 0xE7, 0x5E, + 0xB6, 0xF3, 0x71, 0x40, 0x58, 0x91, 0x5D, 0xE0, 0xEE, 0x18, 0x4D, 0x8C, 0x55, 0x30, 0x0F, 0x57, 0x6A, 0x8B, 0x82, 0xA8, 0x63, 0xE8, 0x1A, 0xF3, 0x34, 0x17, 0xBD, 0x4C, 0xFC, 0x94, 0xE7, 0xA6, + 0x12, 0x63, 0xB3, 0x9F, 0x01, 0xF6, 0xE2, 0xE7, 0x07, 0x48, 0xB6, 0xE5, 0xE5, 0x9C, 0xF6, 0xCA, 0x01, 0xB0, 0x02, 0x8C, 0x93, 0xBB, 0xBC, 0xEB, 0xC5, 0x48, 0xF9, 0x87, 0xF1, 0x07, 0x55, 0xBF, + 0x33, 0xCA, 0x58, 0x5C, 0xB4, 0x1C, 0xF5, 0x78, 0xDF, 0x5F, 0xFE, 0x37, 0x92, 0x4E, 0x3C, 0x2C, 0x07, 0x2E, 0xD1, 0xDA, 0xC9, 0x16, 0x21, 0x76, 0x97, 0x29, 0x71, 0xE7, 0x9B, 0x62, 0xFB, 0x20, + 0x8F, 0x1A, 0x73, 0xBF, 0x03, 0x61, 0xE2, 0x99, 0x3D, 0xCC, 0xCD, 0x31, 0x10, 0xC3, 0x4D, 0x83, 0x9D, 0x18, 0xDD, 0x43, 0xA5, 0xE8, 0xF0, 0xD9, 0x41, 0xE9, 0x9A, 0xDC, 0xF4, 0x41, 0x40, 0x5F, + 0x32, 0x10, 0x76, 0x71, 0xB2, 0xD8, 0xB2, 0x24, 0x4F, 0x7B, 0xA9, 0x2D, 0xCE, 0xD5, 0x87, 0xA2, 0x10, 0xFE, 0x8F, 0xF4, 0x3C, 0x61, 0x6A, 0xCB, 0x5E, 0x76, 0x6E, 0x6A, 0xF2, 0xCE, 0xB0, 0x35, + 0x99, 0xBA, 0x3D, 0xE3, 0x76, 0xEB, 0x57, 0x35, 0xEF, 0x16, 0x14, 0x39, 0x53, 0xD1, 0xFD, 0xDB, 0x7E, 0x9F, 0x28, 0x74, 0xB0, 0xD6, 0x08, 0x3D, 0xD7, 0xEC, 0x43, 0x86, 0xAE, 0x00, 0x3F, 0x51, + 0xCC, 0xF2, 0xD2, 0x1E, 0xF6, 0x05, 0x91, 0x63, 0xC5, 0x15, 0x21, 0x74, 0x42, 0x3F, 0x57, 0x11, 0x9D, 0x0F, 0xCE, 0x62, 0x7D, 0x76, 0x3D, 0x81, 0xC1, 0x0A, 0xA1, 0x32, 0x9F, 0x74, 0xC8, 0xD4, + 0x45, 0x43, 0x7B, 0xA6, 0x71, 0x8A, 0x33, 0xDB, 0x6E, 0x79, 0x37, 0x51, 0x72, 0xB2, 0xAE, 0x35, 0x91, 0x82, 0x19, 0x78, 0xD5, 0x20, 0x82, 0x4E, 0x2D, 0x2F, 0xF8, 0x98, 0xB7, 0xF4, 0xC8, 0x67, + 0xFF, 0x46, 0x27, 0x22, 0xBC, 0x07, 0xEA, 0xDA, 0xD3, 0x89, 0xA9, 0x10, 0xB6, 0xF6, 0x54, 0x29, 0xDA, 0x12, 0x97, 0x35, 0xFE, 0x04, 0x9E, 0x3E, 0xCB, 0x38, 0x89, 0xF6, 0x04, 0x7C, 0xF2, 0xBD, + 0x2A, 0x88, 0xD5, 0x0A, 0x65, 0x1B, 0x32, 0x35, 0xD2, 0x48, 0x0E, 0x1D, 0xA5, 0xA3, 0x52, 0x47, 0xFA, 0x76, 0xC8, 0x31, 0x73, 0x63, 0x99, 0xD3, 0x7E, 0x8D, 0x03, 0x3C, 0x1D, 0x05, 0x1C, 0x9B, + 0x6A, 0x99, 0xAB, 0x80, 0xB1, 0x31, 0x3F, 0xA2, 0x4C, 0x5C, 0x59, 0x76, 0x6E, 0x6C, 0x51, 0xA3, 0x8F, 0xE9, 0xF1, 0x18, 0x6A, 0x76, 0x7E, 0xEB, 0xD0, 0xD8, 0x80, 0x01, 0xAE, 0x02, 0x46, 0xCD, + 0x4E, 0xBE, 0x2C, 0x97, 0x9D, 0xE8, 0x2C, 0x30, 0xBB, 0xDB, 0x98, 0xB4, 0x74, 0x4F, 0x11, 0xF9, 0xE6, 0x39, 0xED, 0xDD, 0x8C, 0x19, 0x4D, 0x79, 0x11, 0x20, 0x1A, 0x8F, 0xA7, 0x45, 0x99, 0x1B, + 0x4D, 0x8A, 0x57, 0x09, 0xB6, 0x2A, 0x21, 0xB6, 0x3B, 0x97, 0x62, 0x91, 0x3D, 0x36, 0xCE, 0x99, 0x5C, 0x2D, 0x6B, 0x79, 0x15, 0x1E, 0x8D, 0x83, 0x83, 0x8C, 0xD1, 0xF3, 0x88, 0x40, 0xA9, 0x41, + 0x72, 0x55, 0xDD, 0x16, 0x6B, 0x7A, 0x35, 0x84, 0x49, 0x90, 0x03, 0xFB, 0x62, 0x56, 0x11, 0x40, 0x4C, 0x95, 0xB9, 0x60, 0xDF, 0x0D, 0xB1, 0xBC, 0xF1, 0x57, 0x4B, 0x09, 0x65, 0xDB, 0xD8, 0x34, + 0xEE, 0x14, 0x81, 0x17, 0xD5, 0xE0, 0x5A, 0x7C, 0xC7, 0xCC, 0x1A, 0x86, 0x56, 0x18, 0xA2, 0xBE, 0x48, 0x54, 0xDB, 0x89, 0x35, 0xCD, 0xA1, 0xE6, 0x8B, 0xD8, 0xD0, 0x9E, 0x72, 0xF0, 0xAC, 0x90, + 0x53, 0xC8, 0x82, 0xC4, 0xAB, 0xA4, 0x00, 0x4A, 0x61, 0x4D, 0x10, 0x50, 0x53, 0x00, 0xB6, 0x17, 0x6C, 0xA1, 0xF3, 0x24, 0xE2, 0x2E, 0x78, 0x24, 0x29, 0x9F, 0x9C, 0x40, 0x75, 0x5B, 0x71, 0xD8, + 0x2B, 0x67, 0x95, 0x47, 0xF0, 0x6A, 0xD4, 0x8B, 0xE6, 0x6D, 0x68, 0x07, 0x2C, 0x93, 0x90, 0x23, 0x3C, 0x93, 0x3F, 0x80, 0xA1, 0x4F, 0x8D, 0x4A, 0x6B, 0x0B, 0x4E, 0x19, 0x70, 0xE1, 0xAC, 0xC1, + 0xBE, 0xA7, 0xF5, 0xD3, 0xBE, 0x22, 0x44, 0x48, 0xF8, 0x57, 0xBA, 0xB6, 0x8A, 0xEF, 0xA6, 0xD8, 0xCB, 0x81, 0x9B, 0x64, 0x29, 0x4A, 0x12, 0x99, 0x79, 0x16, 0xCD, 0xBF, 0x56, 0xE9, 0xA8, 0xD0, + 0x02, 0xDD, 0x06, 0x5F, 0x12, 0xC6, 0x18, 0x23, 0xF4, 0xFC, 0x21, 0x45, 0x08, 0x23, 0x2E, 0x43, 0x1F, 0x0B, 0x68, 0x98, 0x47, 0x5B, 0xB5, 0xDD, 0x0D, 0x7D, 0x52, 0x8E, 0x84, 0x0C, 0x22, 0x80, + 0x9A, 0xF7, 0xE1, 0x53, 0x63, 0x72, 0x4A, 0x61, 0x3A, 0xCC, 0xFB, 0xE2, 0xB3, 0x74, 0x38, 0xC1, 0x59, 0xCE, 0x14, 0xCB, 0x0C, 0x98, 0xBF, 0xD4, 0x99, 0xC0, 0x8D, 0xAC, 0x0C, 0xF4, 0x5D, 0x82, + 0x1C, 0xC2, 0xFA, 0x47, 0x31, 0x9B, 0x6F, 0xB4, 0xCE, 0xD7, 0xE5, 0x98, 0x5E, 0xC8, 0x27, 0x4D, 0xE0, 0x90, 0x71, 0xD3, 0xC1, 0x0D, 0xA5, 0xBF, 0x9E, 0x52, 0x2B, 0x01, 0xCE, 0x91, 0xD6, 0x6B, + 0x91, 0x79, 0x5D, 0x3D, 0x22, 0xC0, 0x04, 0x83, 0x45, 0x42, 0x75, 0xDD, 0x2B, 0xBD, 0xD7, 0xC2, 0xDC, 0xC4, 0xA1, 0x67, 0xE5, 0xD7, 0xFC, 0xDB, 0xB9, 0xF6, 0x20, 0x8C, 0xD4, 0xC9, 0xA4, 0x85, + 0xFA, 0xAE, 0xB8, 0x09, 0xA7, 0x71, 0x1D, 0xAC, 0x28, 0x65, 0xCE, 0xD4, 0x30, 0x64, 0x74, 0xB2, 0x2B, 0x44, 0x48, 0xF8, 0x5D, 0xF3, 0x34, 0x17, 0xF3, 0xFA, 0xCE, 0x1C, 0x05, 0xD4, 0x27, 0x03, + 0xED, 0x31, 0x30, 0x42, 0xA0, 0x5D, 0xE0, 0x36, 0x27, 0x40, 0x13, 0x01, 0x88, 0xEC, 0xB4, 0x45, 0xBB, 0x25, 0x5D, 0xC7, 0x6E, 0xE8, 0x44, 0x3F, 0x73, 0x31, 0x17, 0xF8, 0x35, 0x1F, 0x17, 0x60, + 0x31, 0x75, 0x55, 0x4F, 0xEB, 0x00, 0xB7, 0xFF, 0x54, 0xD8, 0x07, 0x86, 0xF3, 0x05, 0xCD, 0xE1, 0x8C, 0xD5, 0xEC, 0x56, 0xEC, 0x09, 0x62, 0xA3, 0xE0, 0x44, 0x82, 0xDC, 0xE3, 0x62, 0x2D, 0x04, + 0x0D, 0x24, 0xC4, 0x0F, 0x2E, 0x8A, 0x14, 0xA4, 0x47, 0x65, 0x9D, 0x6C, 0x56, 0x1F, 0x2F, 0xFE, 0xE6, 0x8F, 0x8D, 0x3D, 0xE5, 0x11, 0xB2, 0x3E, 0x8B, 0x17, 0x2A, 0x01, 0xA3, 0xED, 0xA4, 0xD3, + 0x78, 0x0E, 0x74, 0xC6, 0x77, 0x24, 0x43, 0x30, 0xE9, 0xAE, 0xFF, 0x01, 0x9F, 0xE0, 0x7B, 0xE3, 0xD3, 0x3F, 0x32, 0x2F, 0x9C, 0xE2, 0x21, 0x4B, 0x9D, 0x9C, 0xFF, 0x99, 0xD0, 0x5A, 0x59, 0xE4, + 0x75, 0x51, 0x43, 0x2A, 0xE7, 0x6F, 0x4C, 0xD4, 0xF8, 0xDD, 0x51, 0x52, 0x0F, 0xFE, 0x81, 0x1B, 0x4B, 0x93, 0xCD, 0x62, 0x19, 0xC8, 0x1B, 0x63, 0xB1, 0xD6, 0x27, 0x78, 0x5C, 0x2A, 0x0F, 0xC2, + 0x2E, 0x3A, 0xEA, 0x86, 0xCE, 0xEE, 0x1F, 0x7F, 0xBC, 0x4E, 0xFC, 0xB4, 0x6D, 0xDF, 0xBC, 0xD8, 0x8A, 0x02, 0xF3, 0xB4, 0xE6, 0x7C, 0x5F, 0xF2, 0xE8, 0xDC, 0x68, 0xBF, 0x16, 0xC7, 0x46, 0x99, + 0xBB, 0xB6, 0x28, 0x90, 0x2F, 0x72, 0xC3, 0xDE, 0xBC, 0x8B, 0xF5, 0xDF, 0x70, 0x6D, 0x47, 0xA6, 0x05, 0xA1, 0x07, 0xDA, 0xA0, 0x01, 0x41, 0x39, 0xCE, 0x40, 0xF0, 0xD4, 0x6D, 0x8D, 0x6D, 0xC7, + }, + .pkcs8_len = 0, + .spki_len = 0, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 3293, + .sig = { + 0xB0, 0x55, 0xB0, 0xE1, 0x76, 0x10, 0xBF, 0x54, 0xB3, 0x3B, 0x96, 0x09, 0x8D, 0x79, 0x6E, 0x98, 0xF7, 0x89, 0x9F, 0x48, 0x56, 0xCB, 0xC8, 0xD7, 0x04, 0xF9, 0xD7, 0x77, 0x8C, 0x18, 0x77, 0xF1, + 0xE1, 0x24, 0xBF, 0x62, 0xA0, 0xD1, 0x7F, 0x01, 0x3B, 0xE4, 0x34, 0x0F, 0xD5, 0x7B, 0x4F, 0xA6, 0x22, 0x2D, 0x9C, 0xDB, 0x90, 0x28, 0xE8, 0xB0, 0x2B, 0x92, 0x6E, 0x15, 0x54, 0xD1, 0x45, 0xF4, + 0x47, 0x98, 0xAA, 0xC2, 0xFA, 0xA2, 0x03, 0x3C, 0x4A, 0xEF, 0xB6, 0xCC, 0xB6, 0xCF, 0xE5, 0xC2, 0xA6, 0x23, 0x8E, 0xE7, 0x9C, 0x5C, 0xC2, 0xF0, 0xE8, 0x04, 0xBE, 0xD1, 0x7F, 0x75, 0xC1, 0xF3, + 0x99, 0x4D, 0xD7, 0xE7, 0xA0, 0xF2, 0xA7, 0x03, 0x4C, 0x0C, 0x8C, 0x98, 0x64, 0x80, 0x40, 0x57, 0xE2, 0xE5, 0x57, 0x67, 0x3F, 0xDF, 0xD6, 0x64, 0x35, 0x6F, 0xAB, 0xD0, 0x51, 0xF9, 0x07, 0x5B, + 0x34, 0x00, 0xA0, 0xC7, 0xE8, 0x45, 0x59, 0x55, 0x3E, 0xDF, 0x98, 0x9B, 0xFF, 0xD2, 0x11, 0x2B, 0x29, 0x60, 0x22, 0x03, 0x06, 0x6B, 0xDE, 0xA7, 0x84, 0x35, 0xEB, 0xC6, 0xE3, 0x81, 0x8C, 0xC9, + 0x2D, 0x61, 0xBC, 0xC1, 0x25, 0xA8, 0x57, 0x5B, 0x5A, 0x8A, 0xEE, 0x42, 0x25, 0xFB, 0x9C, 0x62, 0x48, 0x3F, 0x3E, 0xD1, 0x18, 0x5A, 0x6A, 0x96, 0x82, 0x2E, 0x5E, 0xFC, 0x1B, 0xA7, 0xCD, 0x8D, + 0x5F, 0xD8, 0xCC, 0x18, 0x7D, 0x2A, 0x26, 0x69, 0xCA, 0xDF, 0x58, 0xFA, 0xD6, 0x62, 0x89, 0x79, 0x4C, 0x96, 0x48, 0x5B, 0x2C, 0x46, 0x45, 0xC7, 0xD3, 0xD3, 0x56, 0x84, 0xB7, 0x42, 0x9B, 0x5E, + 0xF3, 0x15, 0x45, 0x76, 0x99, 0xBE, 0x80, 0x30, 0xBC, 0x3D, 0xEB, 0x81, 0x66, 0x60, 0x2A, 0xC5, 0x48, 0x19, 0x82, 0x48, 0x83, 0xA2, 0x46, 0xC8, 0xA1, 0xA3, 0x4F, 0xC8, 0x9B, 0x2F, 0xE0, 0x32, + 0x9B, 0x5C, 0xA0, 0x5D, 0x4E, 0x14, 0xB6, 0xDF, 0xFC, 0x21, 0x44, 0x60, 0x6A, 0xB3, 0x60, 0xBB, 0x3B, 0x8A, 0xC5, 0xA1, 0x78, 0x99, 0x8B, 0x46, 0x21, 0x81, 0x81, 0xCA, 0xC8, 0xDE, 0x4C, 0x29, + 0x48, 0x30, 0xD4, 0x9D, 0x8F, 0x00, 0xEC, 0x12, 0xC3, 0xD3, 0xAC, 0x7B, 0x4A, 0x2C, 0x30, 0x17, 0x58, 0xE6, 0x8A, 0x56, 0x81, 0x17, 0x7F, 0xF2, 0xA7, 0x5D, 0x1D, 0x4B, 0xF1, 0xC9, 0x26, 0x88, + 0x0B, 0x34, 0xB7, 0x28, 0xF7, 0xC3, 0x2E, 0x40, 0x60, 0x99, 0xD9, 0x5A, 0xB4, 0x48, 0x92, 0xF7, 0x48, 0xAA, 0xFE, 0xB5, 0x5B, 0x26, 0xBE, 0x31, 0x75, 0x12, 0xB0, 0x37, 0x7D, 0xBE, 0x89, 0x1A, + 0xC5, 0x45, 0x6A, 0x92, 0x4C, 0x36, 0x83, 0x9B, 0xC8, 0x01, 0xDB, 0x2A, 0xC5, 0xB7, 0x11, 0x0A, 0x9B, 0xAF, 0x4C, 0x3C, 0x49, 0xD0, 0x05, 0x39, 0x3C, 0xDF, 0xFA, 0xD4, 0xF9, 0x68, 0x61, 0x20, + 0xF4, 0xFD, 0xE0, 0x16, 0x8A, 0x9E, 0x45, 0x8E, 0x72, 0x9F, 0x4B, 0x0A, 0xE1, 0xA4, 0xC4, 0x12, 0x4C, 0xA3, 0x4D, 0xF5, 0xB6, 0x3B, 0xC2, 0xE7, 0xCB, 0xEE, 0x01, 0xA3, 0x8D, 0x31, 0xA0, 0xED, + 0x8D, 0x3C, 0x4C, 0x38, 0x03, 0xC3, 0xC2, 0x4C, 0x5C, 0xAD, 0xEB, 0xE3, 0xE9, 0x1A, 0x8D, 0x2E, 0x1B, 0xFC, 0xF0, 0x50, 0x8A, 0x27, 0x88, 0xD8, 0x9D, 0xFE, 0xA2, 0x0F, 0xD6, 0x38, 0x18, 0xB8, + 0x39, 0x60, 0xA6, 0xCF, 0x93, 0x08, 0x72, 0xB9, 0x57, 0x85, 0x57, 0x50, 0x88, 0xCF, 0x7E, 0x8B, 0x63, 0xA1, 0x89, 0x5A, 0x8C, 0x1C, 0x77, 0xA8, 0x4C, 0xB9, 0xCC, 0x6B, 0xD1, 0xD5, 0xFA, 0x93, + 0x96, 0x77, 0xAF, 0x17, 0xEE, 0xBE, 0x2D, 0x2E, 0xE6, 0x84, 0xC6, 0x60, 0x15, 0xF1, 0xBB, 0x14, 0x2A, 0x72, 0x77, 0x79, 0x58, 0x0D, 0xA1, 0xBC, 0x5E, 0x97, 0x5A, 0xA5, 0x6E, 0xF5, 0xD7, 0x7A, + 0x84, 0x07, 0xE5, 0x06, 0xA5, 0xDE, 0xEE, 0xA5, 0xE8, 0xB0, 0x79, 0x7F, 0x10, 0x64, 0x60, 0x05, 0x64, 0x80, 0x22, 0x21, 0x3C, 0xCB, 0x86, 0xA7, 0x7D, 0xF5, 0xD7, 0xB3, 0x16, 0xE8, 0x5D, 0x55, + 0xB9, 0xDA, 0x0F, 0xDF, 0xD5, 0xF2, 0x35, 0x52, 0xDD, 0x47, 0xCC, 0xFA, 0x96, 0x4A, 0xC3, 0x9E, 0xE6, 0x84, 0xBD, 0x63, 0x79, 0x3B, 0xB7, 0xDC, 0xAB, 0x69, 0xBE, 0x7E, 0xD9, 0x4D, 0x8D, 0xDB, + 0xA1, 0x85, 0xE8, 0x0A, 0x7A, 0xAE, 0xE7, 0x4E, 0x87, 0x8F, 0x50, 0xA2, 0x13, 0xF3, 0xB4, 0xFF, 0xB6, 0x6E, 0x6D, 0x34, 0xA3, 0x9C, 0x0A, 0xAE, 0x2B, 0x1D, 0x61, 0x36, 0x6F, 0xE4, 0x03, 0x53, + 0x9C, 0x69, 0xA0, 0x88, 0x75, 0x1F, 0x56, 0x90, 0x1A, 0x10, 0xBC, 0x44, 0x23, 0x13, 0xA3, 0x5C, 0x2D, 0x83, 0x54, 0x76, 0xD0, 0xFA, 0xD4, 0x47, 0xC7, 0x70, 0x08, 0x0F, 0xA4, 0x1B, 0xF3, 0x8D, + 0x68, 0x5F, 0xB3, 0x1B, 0x11, 0xA7, 0xD2, 0xE6, 0xFB, 0x52, 0x67, 0x3D, 0x16, 0x87, 0x23, 0xE6, 0x89, 0x08, 0xC0, 0x67, 0x2A, 0x0F, 0x36, 0xE2, 0x5A, 0x19, 0x9E, 0x17, 0xA6, 0xFE, 0x5B, 0x8B, + 0x82, 0x5B, 0x96, 0xEA, 0xB7, 0xAB, 0x4B, 0x7D, 0x83, 0x81, 0xDB, 0xC5, 0x00, 0x31, 0xA5, 0xF2, 0xE0, 0x9E, 0x4B, 0xE8, 0x71, 0x53, 0x3A, 0xDC, 0x5D, 0x08, 0xD0, 0x09, 0x42, 0x9B, 0xBF, 0x5C, + 0x86, 0xF8, 0x12, 0x0D, 0x09, 0x5C, 0x8E, 0xEC, 0xBE, 0xF3, 0xE0, 0x99, 0xDE, 0x61, 0x8D, 0x43, 0x77, 0x24, 0x1B, 0x50, 0x36, 0x9E, 0xDE, 0x51, 0xAA, 0x74, 0xAB, 0x96, 0x65, 0x89, 0xE2, 0xC6, + 0x87, 0xD6, 0xC0, 0x9F, 0xAC, 0x9C, 0x6D, 0x6C, 0x54, 0x61, 0xF5, 0xA6, 0x30, 0x08, 0xE9, 0x83, 0x5F, 0xF4, 0xB5, 0xBD, 0x42, 0x65, 0xF1, 0x12, 0x8C, 0x09, 0x2C, 0x27, 0xD4, 0xDA, 0x50, 0x8F, + 0xD4, 0xF5, 0x0E, 0xFA, 0x74, 0xA7, 0x31, 0x57, 0x05, 0x9A, 0x4B, 0x2F, 0x41, 0xFE, 0x8B, 0xF9, 0x67, 0x16, 0x79, 0x69, 0xB9, 0x3B, 0xF5, 0x20, 0x45, 0x84, 0x26, 0x90, 0x32, 0x42, 0x9E, 0x35, + 0x77, 0x70, 0x4B, 0xDF, 0x68, 0x98, 0x00, 0xDD, 0x8B, 0xDE, 0x82, 0x6B, 0x74, 0xCE, 0xF5, 0x10, 0xA1, 0xE0, 0x87, 0x02, 0x3F, 0x09, 0x26, 0xE9, 0x7F, 0x37, 0x92, 0x6B, 0x16, 0xEF, 0x78, 0x6C, + 0x37, 0xEC, 0x21, 0xF2, 0x40, 0x71, 0x04, 0xD3, 0x95, 0x4A, 0x7A, 0x07, 0xC3, 0x0D, 0xE2, 0xD6, 0x78, 0x84, 0x02, 0xD7, 0x1A, 0x56, 0x2E, 0xA5, 0x4C, 0x79, 0xB4, 0x19, 0x7D, 0x20, 0x2C, 0x97, + 0x72, 0x5D, 0x2D, 0x8B, 0x7E, 0x73, 0x32, 0xF3, 0xFF, 0x1A, 0x6F, 0xAD, 0x49, 0xA4, 0xC0, 0x0C, 0xD1, 0xA4, 0x47, 0x65, 0x1B, 0x8E, 0x08, 0xD8, 0x50, 0x6B, 0xCA, 0x82, 0x3E, 0x10, 0xEF, 0x41, + 0x16, 0xE6, 0xCF, 0x49, 0x67, 0x5C, 0x43, 0x30, 0xA1, 0xDE, 0x19, 0x08, 0xDD, 0xB5, 0x9F, 0x7E, 0xA5, 0xF8, 0x9C, 0x94, 0xCE, 0x50, 0x0F, 0x82, 0xB4, 0x3C, 0xE7, 0x89, 0x15, 0x84, 0x73, 0xB9, + 0xE0, 0x79, 0x05, 0xD8, 0xE8, 0x61, 0x5E, 0xDE, 0xF0, 0x21, 0x38, 0x3F, 0xC3, 0x1D, 0x61, 0x8C, 0x5C, 0xE6, 0x25, 0x65, 0x3B, 0x40, 0xC2, 0x1B, 0xD7, 0xE0, 0xBC, 0x78, 0x3D, 0x93, 0xBE, 0xC1, + 0xB7, 0xA5, 0xB4, 0xBB, 0xC6, 0xC2, 0x81, 0xB7, 0x77, 0x55, 0x47, 0x39, 0x0E, 0xF3, 0xD3, 0x0E, 0x27, 0x73, 0x99, 0x36, 0x93, 0x08, 0xD8, 0xA1, 0xCD, 0xC2, 0xE1, 0xDB, 0xD6, 0xF1, 0x58, 0x97, + 0x0A, 0xC2, 0xAC, 0x5C, 0x2C, 0x94, 0x81, 0x97, 0x5B, 0x80, 0x95, 0x80, 0xC0, 0xEA, 0x89, 0x91, 0x2C, 0x07, 0x66, 0xF4, 0x58, 0x30, 0xA8, 0x96, 0x3F, 0xBB, 0x7E, 0x17, 0xD8, 0x43, 0x85, 0x17, + 0x5A, 0x6E, 0x07, 0x54, 0x68, 0x3C, 0xBF, 0xBB, 0xA6, 0x36, 0x45, 0x94, 0xF6, 0xB5, 0x00, 0x5C, 0x15, 0xBD, 0x5F, 0x85, 0x73, 0x2B, 0x5A, 0x63, 0xF2, 0x62, 0x67, 0xAB, 0x17, 0x04, 0x8C, 0x61, + 0x99, 0x20, 0x00, 0x19, 0xAD, 0xD6, 0xA4, 0xD1, 0xAC, 0xD0, 0x40, 0x5C, 0x38, 0x76, 0x66, 0xE8, 0x71, 0x11, 0xB9, 0x82, 0x5A, 0xFB, 0x97, 0x51, 0xCD, 0x3F, 0x9D, 0x8A, 0x45, 0xC6, 0xB2, 0x08, + 0xD2, 0xD3, 0x33, 0xB6, 0xC5, 0x9F, 0x98, 0xBC, 0xF2, 0x84, 0xC8, 0x54, 0xCF, 0x7D, 0x4F, 0x67, 0x54, 0xFD, 0x75, 0xEE, 0x06, 0x8C, 0x88, 0x67, 0x8E, 0xE7, 0x56, 0x5B, 0x47, 0xB3, 0x6E, 0x68, + 0xA1, 0xFD, 0x7B, 0xB6, 0x0E, 0x2A, 0x8E, 0x0D, 0xF7, 0x12, 0x70, 0x20, 0xF5, 0xC6, 0x27, 0x7B, 0x3E, 0xE0, 0x58, 0x77, 0x3F, 0x9B, 0xBF, 0x1D, 0xC2, 0xE3, 0x98, 0xBC, 0x30, 0x12, 0x02, 0x12, + 0x1C, 0x69, 0x9C, 0x00, 0x37, 0x9D, 0x83, 0x50, 0x09, 0x96, 0x26, 0xF9, 0x09, 0x23, 0x65, 0x92, 0x40, 0x08, 0xB1, 0xA9, 0xCD, 0x9F, 0x87, 0x87, 0x82, 0x2B, 0xEE, 0x96, 0x1A, 0xBA, 0x23, 0x9C, + 0xDC, 0xB4, 0x18, 0xE9, 0x38, 0x60, 0xEF, 0x34, 0x8A, 0x5E, 0x96, 0x45, 0x38, 0x9A, 0x0A, 0x87, 0x8D, 0x39, 0x4F, 0x36, 0x5A, 0xEB, 0xFE, 0x28, 0x0B, 0xEE, 0x68, 0x74, 0xA3, 0x05, 0x4C, 0xD9, + 0x8C, 0xBD, 0x87, 0x16, 0x66, 0x28, 0x04, 0x72, 0x9F, 0xD4, 0x6F, 0xCE, 0xA9, 0xC4, 0xCF, 0x92, 0x9F, 0x2F, 0x12, 0x00, 0x06, 0xCE, 0xBC, 0xC0, 0xBF, 0x75, 0x69, 0x2D, 0x63, 0xC0, 0x44, 0x63, + 0x5D, 0x1A, 0x1D, 0xB6, 0x1A, 0xD1, 0x78, 0x94, 0x15, 0xE5, 0xF2, 0x24, 0x2B, 0x74, 0x00, 0xA8, 0xA7, 0x93, 0x68, 0xED, 0x60, 0x2C, 0x33, 0x64, 0x92, 0xF2, 0x70, 0x34, 0x5B, 0xE9, 0x8B, 0x2D, + 0xD6, 0xEA, 0x8E, 0x4C, 0x53, 0xAC, 0xA3, 0x6E, 0x3C, 0x9B, 0xA2, 0x88, 0xF2, 0x75, 0x86, 0x13, 0x4C, 0xF0, 0xB5, 0xCA, 0x9B, 0xA1, 0xEE, 0xDF, 0x20, 0xD1, 0xAB, 0x4F, 0x2D, 0x08, 0xF3, 0xB0, + 0x42, 0xDB, 0x89, 0xDE, 0xCF, 0xFD, 0xD2, 0x38, 0x54, 0xF3, 0x51, 0x20, 0xAD, 0xDE, 0x16, 0x03, 0x33, 0x5D, 0x56, 0x8D, 0xA9, 0x58, 0x91, 0xCF, 0x3A, 0xB2, 0x1D, 0x9A, 0xFA, 0xF6, 0x6C, 0x28, + 0x6C, 0x13, 0x00, 0x01, 0x9C, 0xA9, 0xBA, 0xF2, 0xFF, 0x3F, 0x67, 0x25, 0x23, 0x0C, 0x4B, 0x26, 0x98, 0x92, 0xF7, 0xA3, 0xDF, 0xD6, 0xEA, 0xB7, 0x4C, 0x31, 0x4A, 0x86, 0xF8, 0xB4, 0x7E, 0xAE, + 0x49, 0xF4, 0x19, 0xE4, 0xA2, 0x91, 0x7B, 0x98, 0x4F, 0xE9, 0xA0, 0x03, 0x32, 0xAF, 0xB7, 0xA5, 0x6E, 0x5E, 0x67, 0x52, 0x23, 0xAE, 0xCC, 0x50, 0x34, 0x20, 0xAF, 0x8B, 0x39, 0xFA, 0xA9, 0x20, + 0xE3, 0xAD, 0xA1, 0xA4, 0x3C, 0xE7, 0xBD, 0x1F, 0x7D, 0xF2, 0x30, 0x1C, 0x90, 0x27, 0xCC, 0x1C, 0xE5, 0x66, 0x6E, 0xB0, 0x93, 0x62, 0x10, 0xAF, 0xA5, 0x9E, 0x10, 0xF3, 0x07, 0xCA, 0x1F, 0x78, + 0x63, 0xED, 0xD6, 0xC3, 0xBB, 0x8F, 0x5D, 0x63, 0xC0, 0xCF, 0x0E, 0xA8, 0xF0, 0x6E, 0xF0, 0x8C, 0xCC, 0x24, 0xC1, 0x4F, 0x29, 0x5D, 0xD2, 0x86, 0xFD, 0x9F, 0x4E, 0x71, 0x02, 0x10, 0x9D, 0x53, + 0xFF, 0x5E, 0xFF, 0x4A, 0x01, 0xDC, 0xAA, 0xD5, 0xFB, 0x60, 0x55, 0xA0, 0x70, 0x3C, 0xD4, 0x71, 0xB2, 0x0B, 0x5F, 0xA4, 0x56, 0x0B, 0xDE, 0xAA, 0x13, 0x13, 0xC7, 0x64, 0x7A, 0xE7, 0x56, 0xAE, + 0x85, 0x91, 0x57, 0x9E, 0xA5, 0x12, 0x0E, 0x09, 0xD6, 0x79, 0x48, 0x40, 0x62, 0x9B, 0x9F, 0xEF, 0xEF, 0xC2, 0x0D, 0xB5, 0x94, 0xBA, 0xDC, 0xD1, 0x29, 0xEC, 0x49, 0x1C, 0x3C, 0xF7, 0x5A, 0xB4, + 0x0C, 0x47, 0x2A, 0xD2, 0x2C, 0x2D, 0xED, 0xBC, 0x77, 0xBA, 0x26, 0x71, 0xC8, 0x43, 0x48, 0x65, 0x60, 0xDC, 0x76, 0x52, 0x31, 0xBF, 0x5F, 0xDC, 0xDB, 0xCC, 0x77, 0xC8, 0x30, 0x0F, 0x9D, 0x2B, + 0x53, 0xEC, 0x34, 0x46, 0xD8, 0x2F, 0x08, 0x7B, 0x89, 0xBD, 0x99, 0x2F, 0x7A, 0xB0, 0xA7, 0x80, 0xB5, 0x38, 0x81, 0x18, 0xBB, 0xF1, 0x7C, 0xCB, 0xEC, 0x2D, 0x19, 0x6F, 0x3E, 0xDC, 0x47, 0x8F, + 0xB9, 0x47, 0xD8, 0x30, 0x2B, 0x04, 0x0A, 0x60, 0xD0, 0xBA, 0xB8, 0x5C, 0x1C, 0x5C, 0x47, 0x4E, 0xAB, 0x41, 0xE0, 0x64, 0x41, 0x06, 0x95, 0xC6, 0x0E, 0x1A, 0xCE, 0xE7, 0x9E, 0x13, 0x7D, 0x70, + 0x2E, 0x4A, 0x31, 0x39, 0x68, 0xA5, 0x57, 0xB9, 0x7C, 0xE6, 0x43, 0x31, 0x88, 0x8B, 0x52, 0x89, 0xCC, 0xB3, 0x7A, 0x66, 0x25, 0xE5, 0x22, 0x73, 0x71, 0x1B, 0x84, 0x64, 0x58, 0xD5, 0xD8, 0xBA, + 0x1A, 0xE4, 0x96, 0x53, 0x78, 0xCB, 0xE9, 0x18, 0xBF, 0x0F, 0x4B, 0xEE, 0xE1, 0xBD, 0x08, 0xFE, 0xCC, 0x66, 0x06, 0xD2, 0xF3, 0x97, 0x0C, 0x87, 0x4B, 0x0A, 0x09, 0xC4, 0x10, 0xE0, 0xC7, 0xD3, + 0xD6, 0x00, 0x4D, 0x93, 0xF0, 0x6F, 0xBC, 0x25, 0x8F, 0x96, 0x4A, 0x96, 0x19, 0xB2, 0xC6, 0xCA, 0x28, 0xA3, 0xA2, 0x52, 0x9B, 0xF4, 0x4F, 0xB9, 0xF2, 0x44, 0x38, 0x2C, 0xBE, 0xF9, 0x93, 0xC4, + 0x18, 0xA3, 0x88, 0x0F, 0x8D, 0x5F, 0xBA, 0x41, 0xF0, 0x58, 0x24, 0xF4, 0xF3, 0x3B, 0x24, 0xB8, 0x86, 0xD1, 0x15, 0xB8, 0x19, 0x81, 0x6C, 0x9B, 0x7D, 0xB5, 0x1F, 0x2A, 0xA0, 0xCC, 0x6B, 0x01, + 0xB6, 0xAB, 0x21, 0x1F, 0xAD, 0x55, 0x28, 0x4C, 0xDC, 0x04, 0x52, 0x47, 0x85, 0x90, 0x59, 0xBD, 0x36, 0x88, 0x7F, 0x3A, 0xE2, 0xB6, 0xCF, 0x7F, 0x87, 0xEC, 0x2D, 0xF3, 0xC8, 0x9D, 0x43, 0xD2, + 0x7E, 0x5E, 0x48, 0x88, 0xBA, 0xE6, 0x5B, 0x69, 0x24, 0xFA, 0x5D, 0xF0, 0xB2, 0xED, 0x44, 0xE3, 0xE3, 0x79, 0x4B, 0x68, 0x90, 0xF9, 0x33, 0xF9, 0xFB, 0xA7, 0xA7, 0x89, 0xFC, 0x63, 0xCE, 0xB7, + 0x43, 0x60, 0xD4, 0xAC, 0x9C, 0x64, 0xF1, 0x0C, 0xFC, 0x0A, 0xB3, 0x74, 0xC7, 0x12, 0xA3, 0xCC, 0x6C, 0x87, 0x6B, 0x22, 0xF6, 0xD9, 0xFE, 0xF1, 0xC3, 0x87, 0xBF, 0x6B, 0xDE, 0x75, 0x79, 0x2A, + 0xF9, 0x09, 0x4E, 0xC1, 0x7E, 0xB8, 0xB5, 0x5D, 0x35, 0x5F, 0xF0, 0xAE, 0x9D, 0x62, 0x11, 0x1A, 0xD8, 0xA3, 0xCB, 0xA4, 0xF5, 0x66, 0x3D, 0x94, 0xA3, 0x8A, 0x43, 0xE3, 0x52, 0x97, 0x9D, 0xB3, + 0xDF, 0xDF, 0x32, 0x98, 0x85, 0x34, 0xCD, 0x45, 0xFD, 0x43, 0x6E, 0x69, 0x9C, 0x46, 0x7F, 0x6D, 0xDD, 0x50, 0x76, 0xB4, 0xE5, 0xF7, 0xF3, 0x82, 0xAF, 0x45, 0xD3, 0x17, 0x0F, 0x25, 0xB5, 0x41, + 0x50, 0xD6, 0x4D, 0x35, 0xA8, 0x18, 0x55, 0xF4, 0xB2, 0x2B, 0xAC, 0x9F, 0xA1, 0x7D, 0xEF, 0xAD, 0x73, 0xB1, 0x4B, 0x15, 0x84, 0x0E, 0x08, 0x70, 0xDA, 0xF5, 0xB9, 0x2A, 0x30, 0xD2, 0x37, 0xBF, + 0x0C, 0x08, 0xCB, 0x8C, 0x9E, 0xBD, 0x41, 0x59, 0xD3, 0xBB, 0x2D, 0x47, 0x4E, 0x3E, 0x10, 0x6C, 0xC4, 0x68, 0xE6, 0xA2, 0x43, 0x35, 0x12, 0x48, 0x10, 0xF4, 0x86, 0xA6, 0x47, 0x3C, 0x26, 0xA5, + 0xD7, 0x83, 0x26, 0x4F, 0xD8, 0xA3, 0x68, 0x5C, 0x09, 0xD4, 0xEF, 0x77, 0xBD, 0x9A, 0x9A, 0x5C, 0x0B, 0x57, 0x8C, 0x95, 0xE7, 0xCA, 0xA3, 0x4E, 0xCE, 0x46, 0xF8, 0x48, 0x37, 0x47, 0xEE, 0x58, + 0x4D, 0xBB, 0x2D, 0x97, 0x20, 0x76, 0xD7, 0x63, 0xB0, 0xB5, 0x50, 0xE2, 0xCA, 0xE8, 0x34, 0x9E, 0x06, 0x09, 0xF1, 0x4F, 0x0A, 0x8F, 0x51, 0x10, 0xCA, 0xA4, 0xCD, 0xAB, 0xDD, 0x44, 0x40, 0xAD, + 0x16, 0x9C, 0x2A, 0xBE, 0x86, 0xEE, 0x1C, 0x68, 0x0D, 0x6E, 0x94, 0x88, 0x29, 0x64, 0xD8, 0x70, 0xCF, 0xEF, 0x70, 0xA4, 0xF4, 0xC0, 0x4B, 0x49, 0xCC, 0x4A, 0x4F, 0xF6, 0xD4, 0xB9, 0xE3, 0x69, + 0x18, 0xC1, 0x8A, 0x6D, 0x5C, 0x4A, 0xF4, 0x7C, 0xCF, 0x09, 0xFF, 0x64, 0xC7, 0x7A, 0xE3, 0xBF, 0xBC, 0xFA, 0x50, 0x4E, 0x16, 0x9E, 0xAB, 0xB3, 0x06, 0x95, 0x1A, 0x28, 0xAF, 0xF2, 0xFA, 0xB7, + 0xA5, 0xBA, 0x47, 0x6F, 0x56, 0x50, 0xBC, 0x7D, 0xA1, 0x92, 0xD4, 0xB0, 0xEB, 0xFA, 0xAB, 0xAB, 0xE7, 0x72, 0xED, 0xE2, 0xA1, 0x07, 0x1D, 0x5C, 0x4F, 0xC3, 0x3C, 0x25, 0x25, 0xE4, 0x0D, 0x08, + 0x2F, 0xA9, 0x35, 0xBD, 0x32, 0xFF, 0x25, 0x06, 0xB3, 0xA1, 0x31, 0xE3, 0x15, 0x81, 0xB6, 0xC9, 0x44, 0xC2, 0x5F, 0x2D, 0x81, 0x75, 0x5C, 0x39, 0xD3, 0xBF, 0xC0, 0xC6, 0xDE, 0x93, 0xE3, 0x55, + 0x57, 0xAB, 0x1C, 0xF3, 0x47, 0x2B, 0x4A, 0x32, 0x98, 0x09, 0x86, 0xA3, 0x1F, 0x88, 0x28, 0x73, 0x52, 0x19, 0x38, 0xD8, 0xBF, 0xFE, 0x97, 0x36, 0x9F, 0xE2, 0x97, 0x46, 0xAC, 0xFC, 0x8F, 0x12, + 0xDE, 0xEE, 0x0E, 0x9A, 0xC3, 0xE1, 0x67, 0x60, 0x20, 0x22, 0x43, 0x43, 0x58, 0xF9, 0xDC, 0x33, 0xB2, 0xD4, 0x40, 0x8F, 0xD0, 0x89, 0x54, 0xF9, 0x74, 0x5A, 0x0B, 0xD6, 0x5B, 0xC7, 0x7E, 0xE8, + 0xBE, 0xA7, 0x1B, 0xFA, 0x76, 0x40, 0xC1, 0x35, 0xED, 0x19, 0xCC, 0x2F, 0x1C, 0x22, 0xE0, 0xD6, 0xB0, 0x2D, 0xA6, 0xDF, 0x24, 0xDB, 0x05, 0xA6, 0x48, 0x0D, 0xB4, 0x52, 0x27, 0xDC, 0xC9, 0x7A, + 0xDC, 0xEC, 0xB3, 0x91, 0x7F, 0x08, 0x6C, 0x6E, 0x98, 0x08, 0x3A, 0x21, 0x2D, 0x54, 0xDC, 0x4B, 0x81, 0x0F, 0x68, 0x9C, 0x4F, 0x98, 0x43, 0xD2, 0xFB, 0x9F, 0x57, 0x26, 0xB8, 0x76, 0x64, 0xCD, + 0x32, 0x2C, 0x28, 0xB6, 0xF1, 0xE0, 0x1F, 0xA9, 0x1A, 0xB3, 0x50, 0x2F, 0xAC, 0x01, 0xAF, 0xCF, 0x52, 0xC9, 0xB3, 0xD2, 0xAA, 0x20, 0xE1, 0xB3, 0x85, 0xEF, 0x47, 0x0C, 0xB3, 0x30, 0x78, 0x19, + 0x8B, 0x5C, 0x43, 0x95, 0xA0, 0x32, 0x9C, 0xB1, 0x0F, 0x9A, 0x4E, 0x96, 0xF4, 0x3E, 0x51, 0x16, 0x1F, 0xAA, 0xE1, 0x90, 0xEB, 0x8C, 0x39, 0x69, 0xCE, 0xC2, 0x97, 0x7B, 0x08, 0xF6, 0x8D, 0x24, + 0xEF, 0xCE, 0x56, 0x65, 0x11, 0xFE, 0xB6, 0x54, 0xCC, 0x5F, 0xA1, 0xFE, 0x67, 0x57, 0x1F, 0x58, 0xD8, 0x48, 0xBE, 0x7C, 0x56, 0x4A, 0xF5, 0x66, 0x39, 0x06, 0x39, 0xF8, 0x16, 0x92, 0xA7, 0xB7, + 0xC0, 0xF9, 0xF5, 0xAD, 0x85, 0xB8, 0x2F, 0x6A, 0x83, 0x2C, 0x9D, 0xA5, 0x2B, 0x6A, 0x47, 0xD2, 0x3F, 0x9E, 0xCF, 0xAD, 0x44, 0x99, 0x83, 0xC9, 0x39, 0x65, 0x46, 0x58, 0xB1, 0x0A, 0xDD, 0xC0, + 0xB4, 0xAA, 0xDB, 0xB7, 0xB8, 0x5E, 0xA6, 0x02, 0xDA, 0x76, 0x17, 0xD1, 0xB4, 0xA4, 0x5D, 0x86, 0xB8, 0xD0, 0x9D, 0x2C, 0x5A, 0x40, 0x2A, 0x67, 0x58, 0xE0, 0x6A, 0xAA, 0x15, 0x4A, 0xD0, 0x96, + 0x67, 0x8C, 0xBD, 0xD9, 0xCA, 0x6F, 0x5D, 0x92, 0xB0, 0xD7, 0x38, 0x50, 0x1E, 0x18, 0xC1, 0xDC, 0xD2, 0x68, 0xDE, 0x01, 0x12, 0x00, 0x59, 0x48, 0x2D, 0xFC, 0xD1, 0x2B, 0x9B, 0xF2, 0x6E, 0x1C, + 0xF3, 0xB0, 0x99, 0x70, 0xC4, 0x3C, 0xF5, 0x62, 0x0C, 0xA8, 0xD4, 0xE2, 0xFD, 0x31, 0xE5, 0xA8, 0x9E, 0xF8, 0xDD, 0x93, 0x17, 0xE6, 0xCF, 0x55, 0xB3, 0xFB, 0x19, 0xC0, 0x72, 0xE9, 0xD5, 0xDD, + 0xB9, 0x74, 0xEF, 0x60, 0x82, 0x71, 0x1E, 0x99, 0x15, 0xD3, 0x43, 0x4E, 0x7D, 0x34, 0xE7, 0xC3, 0x25, 0xA8, 0xD9, 0x2B, 0x66, 0xB0, 0x83, 0xDF, 0xD6, 0xCF, 0xD1, 0x62, 0xFD, 0x66, 0x65, 0xDF, + 0x9A, 0xBF, 0x18, 0x8F, 0x2D, 0xC5, 0x83, 0xFD, 0xFA, 0xBC, 0x99, 0x7D, 0x78, 0x70, 0xE9, 0x11, 0xD3, 0xC5, 0xEB, 0x5B, 0xDF, 0x80, 0xBA, 0x8D, 0xE6, 0xC4, 0x6C, 0x88, 0xE0, 0x49, 0xD3, 0x9E, + 0x2F, 0xA2, 0x96, 0xCB, 0xE0, 0x69, 0xCA, 0x69, 0x49, 0x4F, 0x89, 0x08, 0x87, 0x67, 0x9C, 0xB3, 0xB0, 0xE6, 0x04, 0x3D, 0x02, 0xB8, 0xF2, 0x4A, 0x3F, 0x14, 0x83, 0xC9, 0x47, 0x81, 0xB6, 0xB0, + 0x1A, 0xF8, 0x01, 0x60, 0x63, 0x99, 0xC3, 0xAC, 0x62, 0x60, 0x3D, 0x86, 0xF7, 0xD5, 0x29, 0x55, 0xC3, 0x12, 0x59, 0x58, 0xC0, 0x4D, 0x57, 0x2A, 0x34, 0x63, 0x4C, 0xD2, 0x36, 0x73, 0x58, 0xA8, + 0x6A, 0xD2, 0xB4, 0x81, 0xB3, 0x26, 0xF2, 0xF8, 0x9D, 0x4B, 0x4D, 0xC0, 0x94, 0xE9, 0x89, 0x18, 0xB5, 0xAE, 0xD8, 0xF4, 0xEB, 0xA4, 0x9C, 0x56, 0x17, 0x2B, 0x16, 0x51, 0xB6, 0x60, 0xB8, 0x70, + 0x47, 0xBA, 0x65, 0x2A, 0x64, 0x0C, 0xA7, 0xB0, 0x69, 0x97, 0x1F, 0xA2, 0xA6, 0x6C, 0x01, 0x95, 0x67, 0xC3, 0x8B, 0x7F, 0x5D, 0x26, 0x21, 0xE7, 0xCB, 0x4B, 0xAA, 0x41, 0x40, 0xEF, 0x5B, 0xB4, + 0x91, 0x96, 0x0D, 0x80, 0xF5, 0x01, 0x01, 0xA0, 0x04, 0xE0, 0x79, 0xF5, 0xB5, 0x1F, 0x39, 0x4B, 0x02, 0x9E, 0x3E, 0xBF, 0xBD, 0xFC, 0x33, 0x59, 0x4E, 0x95, 0xF6, 0xA3, 0x7B, 0xC4, 0xF6, 0xA3, + 0x29, 0xB5, 0xC1, 0xD8, 0xE0, 0x41, 0x45, 0x40, 0x3D, 0x33, 0xA5, 0xC7, 0x04, 0xB3, 0x43, 0x51, 0x82, 0x31, 0xB0, 0x86, 0x46, 0xE4, 0xDA, 0x9D, 0x5A, 0x4E, 0xCA, 0xBC, 0xF5, 0x0F, 0x2B, 0x39, + 0x21, 0xE8, 0x5A, 0x84, 0xC4, 0x09, 0xA1, 0xF6, 0x27, 0xEE, 0x0F, 0x6E, 0xB1, 0xB1, 0xB9, 0xA9, 0xFC, 0xCA, 0x9C, 0xBD, 0x65, 0xCE, 0xA9, 0x00, 0x88, 0x79, 0x7D, 0xF7, 0x51, 0x0B, 0x86, 0x1B, + 0x86, 0xCA, 0x4E, 0x99, 0x8A, 0xF0, 0x75, 0x94, 0x9B, 0x16, 0x7C, 0xBD, 0x66, 0xBC, 0xBE, 0x4C, 0x51, 0x30, 0x34, 0x7D, 0x87, 0x7C, 0xE5, 0xA8, 0x47, 0x9F, 0x4D, 0x56, 0xD3, 0x98, 0x14, 0x6C, + 0xE2, 0xF1, 0xA7, 0x85, 0x42, 0x8D, 0xDD, 0xED, 0xAD, 0x66, 0xAA, 0xB2, 0x87, 0xCA, 0xAE, 0x59, 0x14, 0x24, 0x35, 0x56, 0x1A, 0x40, 0x1B, 0x50, 0x93, 0x43, 0x92, 0xD4, 0x32, 0x9C, 0x3C, 0x21, + 0xAE, 0x48, 0x32, 0x86, 0x53, 0xE3, 0xAE, 0x57, 0x5E, 0x18, 0x1D, 0xB3, 0x89, 0xBE, 0x43, 0x97, 0x16, 0xF6, 0xE3, 0xF3, 0xE2, 0xDC, 0x61, 0xE4, 0xEC, 0xCF, 0xE5, 0x48, 0xAB, 0x7D, 0x71, 0x5E, + 0xAB, 0x49, 0xCF, 0xD7, 0x64, 0x1D, 0xC3, 0x7F, 0x5C, 0x0C, 0x0C, 0x34, 0x96, 0x5C, 0x06, 0xA1, 0x56, 0x70, 0x5F, 0x98, 0x69, 0x58, 0x79, 0x1A, 0x59, 0xCD, 0x5B, 0x48, 0x90, 0xD9, 0xA1, 0xB1, + 0xCF, 0x08, 0x54, 0x1A, 0x7A, 0x93, 0xD0, 0x65, 0xDC, 0xF3, 0xB9, 0xF6, 0xC5, 0x13, 0xC0, 0x27, 0x94, 0x37, 0xD4, 0xBD, 0xBE, 0x62, 0x71, 0x40, 0xD2, 0x94, 0x63, 0x26, 0x39, 0xB7, 0x46, 0x89, + 0x1C, 0xA9, 0x70, 0xDF, 0x6D, 0x73, 0x21, 0xF1, 0xA9, 0x13, 0xAD, 0x9B, 0xED, 0x3F, 0xE0, 0xBC, 0x02, 0xAF, 0xBB, 0x87, 0x20, 0xB7, 0x42, 0xEB, 0x40, 0x9E, 0xB8, 0x2C, 0x66, 0x96, 0x7F, 0x60, + 0xEB, 0xF4, 0xCE, 0xE2, 0x50, 0x8E, 0xF7, 0xF7, 0x03, 0x5B, 0x7F, 0xC7, 0xD9, 0x17, 0x8E, 0x73, 0xED, 0xA0, 0x52, 0x9B, 0xCC, 0x9E, 0xB2, 0x0B, 0x9C, 0xD7, 0x74, 0xC5, 0x64, 0x88, 0x2D, 0xD5, + 0x7C, 0xCF, 0xB5, 0x46, 0x63, 0xCF, 0xA8, 0x1B, 0x91, 0x4E, 0x14, 0xC4, 0xD7, 0xD7, 0x4B, 0xCE, 0x13, 0x9B, 0x7E, 0xC5, 0x3E, 0xA6, 0x1B, 0x0B, 0xF0, 0xDB, 0x61, 0xC7, 0x3A, 0x7A, 0x95, 0xF5, + 0x96, 0xE1, 0x28, 0xEC, 0xA7, 0xA8, 0xC9, 0xEB, 0x92, 0xC2, 0x94, 0x4E, 0xF5, 0x64, 0x94, 0x3E, 0xDA, 0xCF, 0xD4, 0x8A, 0x5A, 0x8B, 0xDC, 0x7D, 0x0F, 0xAB, 0xFA, 0xB6, 0xDA, 0xD3, 0xC5, 0xFE, + 0xEE, 0xB1, 0x39, 0x81, 0x8C, 0x85, 0x73, 0xA7, 0xBD, 0x75, 0x06, 0xB1, 0x8B, 0xFC, 0xE2, 0xBA, 0x15, 0x10, 0x5B, 0x7C, 0xEC, 0x83, 0x09, 0x6C, 0x8C, 0xAE, 0x99, 0xFB, 0xE5, 0xEA, 0x2C, 0x10, + 0xF1, 0xBC, 0xF3, 0xF1, 0x58, 0x26, 0xA0, 0xD8, 0xEC, 0xA9, 0x7C, 0x42, 0xBB, 0x17, 0xCB, 0x9B, 0xED, 0x21, 0x9A, 0x8C, 0xDA, 0x9A, 0x57, 0x62, 0x85, 0x7E, 0xFB, 0xA4, 0x3B, 0x7F, 0x34, 0x15, + 0x7A, 0xEB, 0x49, 0x2F, 0x81, 0xD2, 0xEA, 0x15, 0x6F, 0xF4, 0x99, 0x12, 0xA4, 0x04, 0x9B, 0xE9, 0x3E, 0x12, 0xA2, 0x26, 0x29, 0x5D, 0x8F, 0x68, 0x5C, 0x89, 0xBD, 0xA3, 0x83, 0x1E, 0xB7, 0x3B, + 0xE4, 0x65, 0x7D, 0xBE, 0x3B, 0x09, 0xC0, 0x9D, 0x1D, 0xAF, 0x94, 0x4C, 0x26, 0x64, 0xE9, 0xBD, 0xE9, 0x17, 0x41, 0x98, 0xFE, 0x3D, 0xBA, 0xE4, 0xDE, 0x09, 0x45, 0x22, 0x9E, 0xDD, 0xF5, 0x96, + 0x1B, 0x2F, 0x3D, 0x71, 0x9F, 0xAB, 0xAE, 0xB9, 0xBB, 0xD0, 0xD6, 0x3F, 0x6B, 0x74, 0xF1, 0x47, 0x70, 0x9C, 0xB2, 0xC5, 0xCD, 0xDD, 0x25, 0x35, 0x41, 0xA2, 0xD4, 0xDB, 0xFE, 0x2F, 0x61, 0x9F, + 0xB6, 0xC0, 0xD8, 0x0D, 0x1D, 0x3D, 0x84, 0x93, 0x98, 0xBD, 0xF1, 0xFB, 0xFE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0B, 0x0F, 0x16, 0x1D, 0x23, 0x2D, + }, + }, + { + .name = "Dilithium Round 3, Level 3 (6-5) KAT 1", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_65, + .rho_len = 32, + .rho = { + 0xB5, 0x41, 0xC1, 0xE9, 0x2C, 0xEA, 0xDD, 0x90, 0x4A, 0x09, 0xEC, 0x08, 0xAD, 0x30, 0x6D, 0x97, 0x47, 0x34, 0xA0, 0x77, 0x86, 0x84, 0x71, 0xE5, 0x8D, 0x07, 0x71, 0x87, 0xC4, 0x66, 0x04, 0xCF, + }, + .seed_len = 32, + .seed = { + 0x95, 0x2D, 0x21, 0x81, 0xAC, 0x1F, 0x62, 0x59, 0x6F, 0x76, 0x7E, 0xFC, 0xA0, 0xB5, 0x5D, 0xB0, 0x92, 0xEF, 0x81, 0xDB, 0x66, 0xF9, 0xFF, 0xF1, 0x5F, 0x13, 0xD7, 0xAE, 0xEA, 0xCD, 0x8B, 0x3A, + }, + .tr_len = 32, + .tr = { + 0x2F, 0x2C, 0xFF, 0x6F, 0x47, 0xA6, 0x66, 0xF4, 0xAA, 0xE3, 0x22, 0xC8, 0xEC, 0xA7, 0x34, 0x32, 0x87, 0x99, 0xBC, 0xD5, 0x1D, 0x74, 0x93, 0x9F, 0x63, 0x5B, 0xEA, 0x9C, 0x37, 0x6A, 0x1F, 0xD5, + }, + .s1_len = 640, + .s1 = { + 0x05, 0x62, 0x52, 0x31, 0x01, 0x18, 0x65, 0x21, 0x53, 0x35, 0x41, 0x52, 0x03, 0x67, 0x04, 0x15, 0x60, 0x14, 0x16, 0x76, 0x16, 0x34, 0x61, 0x06, 0x86, 0x87, 0x65, 0x58, 0x02, 0x61, 0x00, 0x71, + 0x02, 0x84, 0x17, 0x70, 0x51, 0x51, 0x55, 0x73, 0x86, 0x43, 0x28, 0x18, 0x46, 0x24, 0x36, 0x82, 0x54, 0x27, 0x68, 0x81, 0x11, 0x56, 0x32, 0x02, 0x40, 0x16, 0x87, 0x63, 0x20, 0x07, 0x36, 0x72, + 0x02, 0x31, 0x72, 0x22, 0x40, 0x43, 0x20, 0x52, 0x01, 0x33, 0x64, 0x34, 0x75, 0x88, 0x30, 0x25, 0x81, 0x06, 0x63, 0x44, 0x35, 0x54, 0x48, 0x71, 0x30, 0x15, 0x82, 0x47, 0x53, 0x74, 0x18, 0x43, + 0x11, 0x88, 0x46, 0x14, 0x31, 0x55, 0x87, 0x03, 0x70, 0x50, 0x04, 0x64, 0x73, 0x43, 0x81, 0x38, 0x37, 0x33, 0x78, 0x65, 0x66, 0x25, 0x75, 0x20, 0x81, 0x45, 0x68, 0x75, 0x11, 0x56, 0x88, 0x43, + 0x22, 0x40, 0x73, 0x80, 0x21, 0x42, 0x80, 0x73, 0x86, 0x60, 0x08, 0x47, 0x10, 0x10, 0x83, 0x40, 0x67, 0x57, 0x38, 0x07, 0x63, 0x10, 0x77, 0x42, 0x27, 0x58, 0x61, 0x46, 0x47, 0x68, 0x31, 0x72, + 0x65, 0x24, 0x11, 0x07, 0x05, 0x35, 0x66, 0x70, 0x67, 0x68, 0x62, 0x80, 0x40, 0x37, 0x85, 0x64, 0x10, 0x40, 0x76, 0x26, 0x28, 0x42, 0x32, 0x02, 0x48, 0x70, 0x17, 0x38, 0x80, 0x88, 0x72, 0x36, + 0x24, 0x17, 0x22, 0x36, 0x71, 0x77, 0x82, 0x46, 0x64, 0x40, 0x16, 0x27, 0x78, 0x81, 0x81, 0x15, 0x11, 0x01, 0x54, 0x45, 0x38, 0x12, 0x81, 0x28, 0x11, 0x74, 0x42, 0x67, 0x15, 0x16, 0x57, 0x08, + 0x02, 0x86, 0x44, 0x83, 0x58, 0x88, 0x17, 0x36, 0x73, 0x61, 0x04, 0x42, 0x32, 0x37, 0x70, 0x50, 0x82, 0x45, 0x17, 0x63, 0x48, 0x72, 0x27, 0x17, 0x70, 0x74, 0x03, 0x85, 0x53, 0x12, 0x11, 0x85, + 0x32, 0x08, 0x01, 0x14, 0x85, 0x56, 0x38, 0x01, 0x27, 0x04, 0x86, 0x07, 0x88, 0x35, 0x04, 0x08, 0x05, 0x66, 0x86, 0x23, 0x01, 0x43, 0x61, 0x43, 0x68, 0x67, 0x42, 0x75, 0x52, 0x72, 0x48, 0x37, + 0x27, 0x47, 0x77, 0x26, 0x55, 0x30, 0x71, 0x82, 0x57, 0x72, 0x71, 0x31, 0x05, 0x65, 0x26, 0x42, 0x12, 0x25, 0x72, 0x78, 0x02, 0x35, 0x54, 0x10, 0x78, 0x28, 0x52, 0x66, 0x72, 0x54, 0x85, 0x77, + 0x47, 0x64, 0x68, 0x43, 0x68, 0x41, 0x57, 0x61, 0x44, 0x40, 0x46, 0x21, 0x15, 0x85, 0x01, 0x44, 0x02, 0x76, 0x66, 0x58, 0x41, 0x55, 0x26, 0x08, 0x48, 0x22, 0x15, 0x04, 0x48, 0x74, 0x43, 0x04, + 0x26, 0x67, 0x66, 0x68, 0x18, 0x67, 0x07, 0x01, 0x02, 0x08, 0x66, 0x76, 0x56, 0x22, 0x26, 0x42, 0x28, 0x81, 0x12, 0x36, 0x61, 0x64, 0x78, 0x01, 0x41, 0x51, 0x04, 0x40, 0x43, 0x13, 0x53, 0x70, + 0x22, 0x44, 0x60, 0x10, 0x75, 0x53, 0x28, 0x68, 0x68, 0x48, 0x17, 0x86, 0x08, 0x24, 0x27, 0x43, 0x23, 0x71, 0x67, 0x04, 0x21, 0x50, 0x21, 0x08, 0x46, 0x84, 0x74, 0x12, 0x88, 0x75, 0x64, 0x67, + 0x14, 0x27, 0x37, 0x18, 0x36, 0x47, 0x52, 0x34, 0x30, 0x24, 0x03, 0x64, 0x67, 0x15, 0x33, 0x43, 0x16, 0x33, 0x76, 0x07, 0x51, 0x11, 0x64, 0x57, 0x28, 0x75, 0x51, 0x58, 0x78, 0x38, 0x70, 0x05, + 0x85, 0x41, 0x81, 0x68, 0x15, 0x82, 0x86, 0x40, 0x35, 0x57, 0x32, 0x27, 0x23, 0x03, 0x13, 0x16, 0x52, 0x05, 0x34, 0x16, 0x76, 0x25, 0x18, 0x57, 0x61, 0x06, 0x01, 0x44, 0x41, 0x71, 0x04, 0x43, + 0x32, 0x01, 0x24, 0x71, 0x88, 0x88, 0x58, 0x58, 0x34, 0x35, 0x86, 0x20, 0x88, 0x72, 0x18, 0x88, 0x44, 0x50, 0x24, 0x77, 0x34, 0x42, 0x64, 0x61, 0x30, 0x61, 0x43, 0x32, 0x31, 0x54, 0x31, 0x45, + 0x56, 0x62, 0x64, 0x08, 0x11, 0x81, 0x50, 0x41, 0x56, 0x14, 0x63, 0x58, 0x33, 0x45, 0x37, 0x57, 0x65, 0x05, 0x12, 0x53, 0x40, 0x65, 0x57, 0x80, 0x57, 0x46, 0x11, 0x57, 0x12, 0x83, 0x07, 0x42, + 0x58, 0x38, 0x87, 0x34, 0x30, 0x05, 0x73, 0x88, 0x46, 0x28, 0x74, 0x43, 0x17, 0x65, 0x81, 0x77, 0x28, 0x74, 0x14, 0x42, 0x06, 0x06, 0x34, 0x73, 0x62, 0x26, 0x61, 0x84, 0x76, 0x20, 0x25, 0x68, + 0x08, 0x65, 0x13, 0x77, 0x83, 0x68, 0x85, 0x55, 0x74, 0x68, 0x32, 0x43, 0x86, 0x70, 0x63, 0x05, 0x30, 0x88, 0x82, 0x44, 0x84, 0x26, 0x86, 0x17, 0x87, 0x31, 0x28, 0x87, 0x33, 0x53, 0x02, 0x81, + 0x88, 0x30, 0x03, 0x51, 0x74, 0x80, 0x53, 0x65, 0x78, 0x17, 0x77, 0x02, 0x61, 0x37, 0x38, 0x36, 0x23, 0x42, 0x35, 0x86, 0x13, 0x00, 0x38, 0x47, 0x58, 0x24, 0x81, 0x84, 0x78, 0x87, 0x77, 0x11, + }, + .s2_len = 768, + .s2 = { + 0x41, 0x51, 0x50, 0x83, 0x02, 0x36, 0x55, 0x53, 0x14, 0x86, 0x41, 0x14, 0x18, 0x51, 0x73, 0x54, 0x86, 0x58, 0x16, 0x74, 0x14, 0x70, 0x76, 0x32, 0x16, 0x38, 0x05, 0x48, 0x85, 0x00, 0x17, 0x23, + 0x87, 0x64, 0x44, 0x86, 0x32, 0x72, 0x45, 0x37, 0x02, 0x58, 0x32, 0x13, 0x44, 0x15, 0x56, 0x02, 0x45, 0x78, 0x70, 0x14, 0x76, 0x84, 0x33, 0x88, 0x04, 0x56, 0x16, 0x57, 0x06, 0x64, 0x01, 0x67, + 0x66, 0x35, 0x37, 0x48, 0x13, 0x43, 0x77, 0x37, 0x01, 0x23, 0x03, 0x82, 0x21, 0x02, 0x00, 0x30, 0x36, 0x47, 0x22, 0x74, 0x67, 0x47, 0x57, 0x42, 0x87, 0x64, 0x03, 0x55, 0x01, 0x05, 0x73, 0x40, + 0x62, 0x78, 0x37, 0x70, 0x16, 0x65, 0x80, 0x22, 0x10, 0x38, 0x48, 0x44, 0x78, 0x04, 0x15, 0x28, 0x27, 0x12, 0x86, 0x53, 0x12, 0x13, 0x46, 0x47, 0x53, 0x82, 0x35, 0x14, 0x33, 0x50, 0x41, 0x77, + 0x05, 0x25, 0x38, 0x31, 0x75, 0x35, 0x02, 0x01, 0x83, 0x86, 0x22, 0x31, 0x16, 0x41, 0x64, 0x55, 0x71, 0x06, 0x32, 0x38, 0x42, 0x81, 0x06, 0x23, 0x86, 0x53, 0x02, 0x84, 0x51, 0x12, 0x74, 0x55, + 0x64, 0x34, 0x28, 0x02, 0x35, 0x30, 0x50, 0x38, 0x58, 0x56, 0x81, 0x54, 0x01, 0x23, 0x50, 0x75, 0x53, 0x53, 0x31, 0x52, 0x55, 0x32, 0x17, 0x74, 0x78, 0x07, 0x84, 0x14, 0x12, 0x30, 0x23, 0x51, + 0x55, 0x10, 0x60, 0x52, 0x15, 0x03, 0x43, 0x72, 0x35, 0x01, 0x17, 0x76, 0x25, 0x10, 0x83, 0x35, 0x84, 0x23, 0x13, 0x63, 0x48, 0x31, 0x54, 0x33, 0x78, 0x64, 0x35, 0x64, 0x58, 0x80, 0x73, 0x12, + 0x55, 0x00, 0x71, 0x15, 0x64, 0x71, 0x34, 0x66, 0x64, 0x66, 0x15, 0x80, 0x50, 0x32, 0x87, 0x05, 0x56, 0x80, 0x74, 0x85, 0x88, 0x46, 0x68, 0x40, 0x36, 0x78, 0x61, 0x22, 0x18, 0x66, 0x20, 0x78, + 0x18, 0x43, 0x60, 0x53, 0x75, 0x70, 0x47, 0x15, 0x58, 0x06, 0x75, 0x73, 0x76, 0x52, 0x11, 0x42, 0x40, 0x10, 0x77, 0x27, 0x16, 0x43, 0x23, 0x46, 0x70, 0x76, 0x05, 0x81, 0x58, 0x27, 0x21, 0x26, + 0x55, 0x02, 0x47, 0x75, 0x41, 0x31, 0x87, 0x37, 0x83, 0x33, 0x28, 0x71, 0x27, 0x68, 0x11, 0x70, 0x34, 0x46, 0x04, 0x62, 0x86, 0x27, 0x12, 0x23, 0x76, 0x44, 0x00, 0x03, 0x44, 0x14, 0x23, 0x03, + 0x34, 0x44, 0x34, 0x38, 0x16, 0x75, 0x32, 0x40, 0x25, 0x52, 0x68, 0x04, 0x45, 0x55, 0x55, 0x04, 0x85, 0x57, 0x05, 0x04, 0x85, 0x80, 0x37, 0x86, 0x40, 0x14, 0x60, 0x80, 0x70, 0x63, 0x28, 0x60, + 0x44, 0x85, 0x21, 0x80, 0x03, 0x00, 0x16, 0x36, 0x23, 0x64, 0x00, 0x32, 0x58, 0x64, 0x67, 0x35, 0x23, 0x15, 0x04, 0x15, 0x26, 0x04, 0x68, 0x52, 0x01, 0x41, 0x02, 0x87, 0x68, 0x21, 0x81, 0x81, + 0x65, 0x83, 0x26, 0x22, 0x16, 0x05, 0x25, 0x76, 0x04, 0x30, 0x14, 0x34, 0x51, 0x74, 0x47, 0x07, 0x31, 0x27, 0x76, 0x64, 0x73, 0x22, 0x64, 0x84, 0x72, 0x77, 0x85, 0x05, 0x73, 0x73, 0x81, 0x22, + 0x34, 0x25, 0x43, 0x00, 0x66, 0x12, 0x58, 0x41, 0x52, 0x36, 0x82, 0x24, 0x33, 0x37, 0x11, 0x65, 0x26, 0x04, 0x83, 0x28, 0x76, 0x27, 0x26, 0x56, 0x87, 0x40, 0x05, 0x08, 0x42, 0x68, 0x48, 0x33, + 0x02, 0x58, 0x53, 0x45, 0x71, 0x20, 0x75, 0x16, 0x14, 0x00, 0x28, 0x54, 0x80, 0x12, 0x66, 0x21, 0x40, 0x53, 0x25, 0x78, 0x67, 0x56, 0x12, 0x25, 0x41, 0x60, 0x21, 0x07, 0x87, 0x74, 0x41, 0x38, + 0x70, 0x63, 0x72, 0x78, 0x75, 0x25, 0x85, 0x83, 0x63, 0x12, 0x65, 0x00, 0x20, 0x74, 0x02, 0x43, 0x18, 0x30, 0x27, 0x14, 0x38, 0x15, 0x42, 0x81, 0x87, 0x34, 0x55, 0x48, 0x78, 0x48, 0x17, 0x68, + 0x01, 0x22, 0x43, 0x70, 0x86, 0x55, 0x04, 0x21, 0x60, 0x24, 0x56, 0x51, 0x50, 0x45, 0x40, 0x44, 0x88, 0x23, 0x73, 0x60, 0x37, 0x56, 0x66, 0x41, 0x11, 0x40, 0x04, 0x55, 0x75, 0x32, 0x07, 0x38, + 0x65, 0x26, 0x65, 0x33, 0x80, 0x30, 0x24, 0x42, 0x32, 0x64, 0x43, 0x08, 0x07, 0x56, 0x05, 0x08, 0x03, 0x58, 0x10, 0x17, 0x63, 0x18, 0x84, 0x48, 0x70, 0x35, 0x16, 0x75, 0x06, 0x40, 0x52, 0x57, + 0x88, 0x43, 0x10, 0x05, 0x65, 0x36, 0x75, 0x40, 0x30, 0x41, 0x26, 0x18, 0x75, 0x34, 0x66, 0x08, 0x54, 0x55, 0x23, 0x61, 0x58, 0x28, 0x82, 0x18, 0x20, 0x84, 0x20, 0x08, 0x75, 0x14, 0x16, 0x66, + 0x11, 0x51, 0x23, 0x36, 0x44, 0x17, 0x42, 0x28, 0x31, 0x12, 0x71, 0x45, 0x66, 0x13, 0x12, 0x67, 0x76, 0x06, 0x83, 0x00, 0x02, 0x82, 0x41, 0x62, 0x05, 0x64, 0x58, 0x22, 0x75, 0x15, 0x74, 0x10, + 0x20, 0x41, 0x83, 0x18, 0x26, 0x05, 0x86, 0x50, 0x11, 0x13, 0x42, 0x47, 0x14, 0x48, 0x84, 0x42, 0x44, 0x83, 0x30, 0x75, 0x21, 0x67, 0x44, 0x13, 0x00, 0x14, 0x53, 0x66, 0x42, 0x54, 0x20, 0x28, + 0x17, 0x88, 0x37, 0x50, 0x45, 0x55, 0x66, 0x34, 0x44, 0x32, 0x14, 0x26, 0x37, 0x75, 0x42, 0x24, 0x84, 0x46, 0x52, 0x18, 0x86, 0x74, 0x58, 0x64, 0x48, 0x16, 0x84, 0x26, 0x62, 0x72, 0x03, 0x70, + 0x27, 0x54, 0x85, 0x17, 0x07, 0x67, 0x22, 0x63, 0x60, 0x35, 0x38, 0x41, 0x15, 0x20, 0x07, 0x52, 0x70, 0x48, 0x25, 0x81, 0x71, 0x17, 0x68, 0x84, 0x16, 0x41, 0x76, 0x20, 0x80, 0x02, 0x84, 0x34, + 0x33, 0x63, 0x77, 0x44, 0x07, 0x70, 0x66, 0x51, 0x75, 0x11, 0x17, 0x55, 0x22, 0x65, 0x03, 0x82, 0x28, 0x13, 0x65, 0x55, 0x78, 0x22, 0x75, 0x26, 0x66, 0x33, 0x18, 0x84, 0x35, 0x75, 0x87, 0x58, + }, + .t0_len = 2496, + .t0 = { + 0xD0, 0xC2, 0x55, 0xD5, 0x1F, 0x82, 0x80, 0xDF, 0x43, 0x10, 0x6E, 0xB1, 0x51, 0xD4, 0x44, 0xAD, 0x6E, 0x4C, 0xAB, 0x4B, 0xAC, 0xC5, 0x85, 0xAA, 0x37, 0xD7, 0x44, 0xB2, 0x45, 0x13, 0x20, 0x40, + 0xDC, 0x3D, 0x76, 0xAB, 0xCE, 0xA9, 0xCD, 0x44, 0x72, 0xC1, 0xCC, 0xA1, 0xF0, 0x7A, 0x49, 0x92, 0xDB, 0xD4, 0xD0, 0x52, 0x4A, 0x48, 0x2B, 0x50, 0x95, 0x71, 0x10, 0x96, 0x2A, 0xEB, 0x75, 0xFE, + 0x2A, 0xCD, 0x2C, 0xA3, 0x84, 0xB2, 0x06, 0xAE, 0x68, 0x98, 0xAE, 0xE2, 0x58, 0x22, 0x18, 0xC0, 0x30, 0x05, 0x9C, 0xF0, 0x61, 0x0D, 0xF2, 0x3F, 0x62, 0xFA, 0x94, 0xCE, 0x63, 0xF5, 0x05, 0x41, + 0x6E, 0xE5, 0x6F, 0x21, 0x3B, 0x1B, 0x04, 0xA3, 0xED, 0x78, 0x6E, 0xDE, 0x5A, 0x02, 0x74, 0xDF, 0xB8, 0x62, 0xB7, 0x64, 0x84, 0x7B, 0x48, 0x2B, 0x73, 0xD1, 0xA3, 0xE4, 0x36, 0x74, 0x43, 0x40, + 0xCC, 0xA3, 0x97, 0x20, 0xC7, 0xDB, 0x10, 0x16, 0x3D, 0x6B, 0x95, 0x2C, 0xDC, 0x3D, 0x8A, 0x19, 0x46, 0x7F, 0xAB, 0xB0, 0x74, 0x89, 0xDE, 0x13, 0x9D, 0x57, 0x2C, 0x8B, 0x74, 0xAB, 0x10, 0x28, + 0x7B, 0xCD, 0x40, 0x20, 0x5D, 0xF4, 0x8A, 0xD5, 0x43, 0x4E, 0xE1, 0x7E, 0xA0, 0x16, 0x99, 0x35, 0x36, 0x38, 0xB7, 0xBE, 0x07, 0x23, 0xE6, 0xC5, 0xF2, 0x76, 0xC9, 0xA5, 0x71, 0x82, 0xB0, 0x99, + 0xEC, 0xE8, 0xE9, 0x2C, 0xF0, 0xF1, 0xD1, 0xCC, 0xAC, 0xAD, 0x71, 0xBC, 0x0C, 0x7C, 0xBC, 0x0E, 0xFE, 0x26, 0x43, 0x31, 0xC2, 0xB4, 0x6F, 0x00, 0x1A, 0x3C, 0x7E, 0x3A, 0xE8, 0x35, 0xA8, 0xD1, + 0x00, 0xF7, 0xF4, 0xD7, 0x1C, 0x18, 0xBA, 0x1E, 0x66, 0x5C, 0xBB, 0xA8, 0xBE, 0x55, 0x9B, 0x8E, 0xD9, 0x55, 0x13, 0x67, 0xE9, 0x50, 0x05, 0x74, 0xEA, 0xDD, 0x85, 0x6E, 0x77, 0x02, 0x43, 0xD0, + 0x7A, 0x30, 0x61, 0xEA, 0xDD, 0x87, 0x97, 0xC5, 0xBA, 0x13, 0x83, 0xC1, 0x39, 0x1E, 0x31, 0x6F, 0xCA, 0x75, 0x2A, 0x9D, 0xD2, 0xD5, 0x30, 0xA8, 0x59, 0xEA, 0xCC, 0x06, 0x06, 0xEC, 0xD0, 0x19, + 0xD8, 0x75, 0xAD, 0xF0, 0x6D, 0x81, 0xC2, 0x5C, 0xE0, 0x7B, 0x30, 0x49, 0x21, 0xC8, 0x22, 0x24, 0xF6, 0x83, 0x95, 0x72, 0x47, 0xA6, 0x62, 0xDD, 0xB7, 0xBA, 0xF0, 0x49, 0x07, 0xCD, 0x17, 0x43, + 0x19, 0x37, 0xA2, 0x6D, 0x62, 0xE1, 0x87, 0xCB, 0xB9, 0xDF, 0x11, 0x35, 0xA0, 0xF0, 0x34, 0x8F, 0xE7, 0xA9, 0x25, 0xF8, 0x6F, 0xCA, 0x96, 0xB2, 0xED, 0x92, 0xE6, 0x9F, 0x45, 0xAD, 0x55, 0xF9, + 0x45, 0xD0, 0xFE, 0x8A, 0xA7, 0xA4, 0x71, 0x91, 0x5B, 0x5F, 0x0F, 0xE9, 0x65, 0x75, 0xCB, 0x2D, 0xEF, 0x41, 0xD5, 0x0D, 0x11, 0x3B, 0xA1, 0xBE, 0x2D, 0x0B, 0x5D, 0x47, 0xDE, 0x93, 0xA1, 0x97, + 0x86, 0xBE, 0xAB, 0x57, 0xEE, 0x1A, 0x03, 0x60, 0xFC, 0xD5, 0xE6, 0x9F, 0x25, 0x6B, 0x12, 0x8D, 0x17, 0xD1, 0xC3, 0x91, 0x63, 0xF1, 0x34, 0x5A, 0xD0, 0xFC, 0xC8, 0x5F, 0xD1, 0x48, 0x8D, 0x78, + 0x78, 0x14, 0xBC, 0x6E, 0x3E, 0x93, 0xD7, 0x1D, 0x24, 0x6F, 0x60, 0xA5, 0x0C, 0xEE, 0x91, 0x13, 0xB3, 0xA8, 0x5E, 0xED, 0x84, 0x28, 0x69, 0x31, 0xB6, 0xCF, 0x66, 0x98, 0x21, 0x5B, 0x29, 0x62, + 0xFD, 0xCB, 0x9E, 0x95, 0x68, 0xCB, 0xC3, 0x84, 0xBE, 0x82, 0x65, 0x58, 0xFF, 0x8D, 0xFF, 0x68, 0xA3, 0xE0, 0x1B, 0x24, 0x70, 0xB7, 0x19, 0x2B, 0x94, 0x92, 0xDF, 0xDE, 0x2C, 0x9F, 0xE0, 0x91, + 0xE8, 0xA6, 0x38, 0xDD, 0x1B, 0xC8, 0x79, 0x4B, 0xA3, 0xB2, 0x77, 0x95, 0xB2, 0x20, 0x69, 0x7B, 0x05, 0xCF, 0x1D, 0x68, 0x59, 0x06, 0xF1, 0x4C, 0xDD, 0x9E, 0x43, 0xE1, 0x11, 0x4B, 0x0A, 0x88, + 0xC0, 0x74, 0x38, 0xEE, 0x1E, 0x69, 0x01, 0xBE, 0x4F, 0x57, 0x7C, 0x78, 0x66, 0x3B, 0x0D, 0x34, 0x39, 0xFB, 0x39, 0x00, 0x95, 0x9A, 0x10, 0x7B, 0xCA, 0xD3, 0x61, 0x10, 0xB4, 0xCD, 0x2B, 0x61, + 0xBE, 0x46, 0xEF, 0x4F, 0x68, 0x00, 0x0D, 0xBC, 0x64, 0xCC, 0xF4, 0x0E, 0x6B, 0x6E, 0xDE, 0x65, 0x77, 0xF8, 0xEA, 0x36, 0x3B, 0x5A, 0x0B, 0xEA, 0x0A, 0x81, 0x91, 0x9B, 0xCF, 0xC1, 0xEC, 0x98, + 0x82, 0xAC, 0x51, 0x40, 0x93, 0x17, 0xEB, 0x24, 0x89, 0x23, 0x34, 0xF4, 0x61, 0xBD, 0xF0, 0x4D, 0x4D, 0x6B, 0x16, 0x91, 0xA7, 0xD4, 0x86, 0x56, 0x25, 0xC7, 0x4E, 0xA7, 0xBB, 0xE2, 0x6B, 0x28, + 0x4B, 0xC4, 0x46, 0x8E, 0x39, 0x5C, 0xE5, 0x62, 0xF8, 0x24, 0xD9, 0x02, 0x9B, 0x83, 0xE7, 0x61, 0x48, 0xDF, 0x2E, 0xE9, 0x62, 0x5C, 0xCF, 0xBB, 0x88, 0x03, 0x94, 0x11, 0xB0, 0x81, 0x67, 0x41, + 0x96, 0xF4, 0xEB, 0xFB, 0xBF, 0x9E, 0x51, 0xD0, 0x47, 0xD0, 0x86, 0xEB, 0xCB, 0xA7, 0xBB, 0xDF, 0x1C, 0xF3, 0x60, 0xC4, 0x03, 0x19, 0xFB, 0x7B, 0x5C, 0xE6, 0xF6, 0xCE, 0x04, 0xE6, 0xAC, 0xB9, + 0xA0, 0xEC, 0x0F, 0x15, 0x15, 0x5E, 0xD5, 0x9D, 0xC1, 0xCC, 0x46, 0x8E, 0xB2, 0x5F, 0x9F, 0x62, 0xC9, 0xD9, 0x24, 0xCB, 0x0B, 0x01, 0x99, 0xA5, 0x27, 0x6D, 0x59, 0xE4, 0x48, 0x38, 0x53, 0x4B, + 0x62, 0xE8, 0x6E, 0x5F, 0xAD, 0x68, 0xC8, 0x1B, 0x2F, 0x0F, 0xC9, 0xAB, 0xE2, 0x4D, 0xAC, 0x0F, 0xF2, 0x65, 0x24, 0x9C, 0x41, 0x0D, 0x96, 0xAA, 0x8E, 0x98, 0x35, 0x4A, 0x6E, 0x23, 0x88, 0x4D, + 0xB4, 0xB5, 0xB0, 0x90, 0xA8, 0xEA, 0x5A, 0x7D, 0xBF, 0x4E, 0x68, 0x12, 0x5B, 0xFD, 0xF7, 0xD2, 0xD6, 0xB3, 0x20, 0xE6, 0x9F, 0x8E, 0x61, 0x72, 0x5B, 0xD5, 0x7F, 0xF4, 0xB9, 0x05, 0xC4, 0xD1, + 0x4F, 0xA1, 0x7D, 0xDB, 0xE9, 0xF2, 0x26, 0x28, 0x3B, 0xC4, 0x62, 0xC1, 0x3E, 0xB7, 0x51, 0x12, 0x1D, 0xBB, 0xE6, 0xC0, 0x2C, 0xBA, 0xCF, 0x43, 0x14, 0x0E, 0x51, 0xBF, 0x9C, 0xFD, 0x39, 0x38, + 0x3E, 0x24, 0x7E, 0xB9, 0x76, 0x0F, 0x8F, 0x40, 0x43, 0xA0, 0x46, 0xF9, 0xDB, 0x54, 0x0D, 0x84, 0x5C, 0x15, 0x73, 0x86, 0x43, 0xBC, 0xFA, 0x3B, 0x8E, 0x27, 0x8B, 0x07, 0x34, 0xBB, 0xEE, 0x3E, + 0xBD, 0xE2, 0x81, 0x09, 0x2E, 0xA3, 0xAE, 0xCB, 0x56, 0xB9, 0x87, 0x4E, 0x4B, 0x9D, 0x3E, 0x2A, 0xCD, 0xC8, 0x04, 0xB2, 0xAE, 0xCE, 0xB9, 0x92, 0xEE, 0x99, 0xAB, 0x11, 0xA3, 0x7C, 0x51, 0x5E, + 0x07, 0xF5, 0xAA, 0xE3, 0x2E, 0x36, 0x70, 0x8B, 0x1C, 0xC0, 0xF4, 0xE2, 0xA6, 0x4D, 0xE5, 0x9A, 0x94, 0xFD, 0x3D, 0xCC, 0x08, 0x9B, 0xD2, 0x94, 0x19, 0x61, 0x42, 0x5F, 0xE9, 0x65, 0xB7, 0x15, + 0xF1, 0x9B, 0x4E, 0xBA, 0xD8, 0xD7, 0x4B, 0x1B, 0x06, 0x01, 0x76, 0x76, 0x0D, 0x7A, 0xD7, 0x3E, 0x45, 0x3E, 0xBF, 0xEB, 0xC7, 0x87, 0x6F, 0xFF, 0xFE, 0x6B, 0xDB, 0x77, 0xFA, 0xB2, 0x0F, 0x0A, + 0x2C, 0x04, 0x31, 0x57, 0xA8, 0xEA, 0x4A, 0xC8, 0x0F, 0x98, 0xA3, 0xC7, 0xB8, 0x24, 0xC1, 0x59, 0xF1, 0x23, 0x6D, 0xA5, 0x2C, 0xE5, 0xA1, 0x0F, 0x0B, 0xC0, 0x25, 0x74, 0x18, 0x61, 0x4D, 0x52, + 0x37, 0xFB, 0x4C, 0x65, 0x3E, 0xC6, 0x65, 0x97, 0xFB, 0x8B, 0xB8, 0x1E, 0xC7, 0xD6, 0xA2, 0x09, 0x9A, 0x9D, 0xD8, 0x37, 0xC4, 0x99, 0xC9, 0x92, 0x77, 0x99, 0xC2, 0xB3, 0xE2, 0xD8, 0xAE, 0x18, + 0xAF, 0xB3, 0xE2, 0x3C, 0x7E, 0x5D, 0x24, 0xDF, 0xA5, 0x79, 0x6D, 0xB5, 0x15, 0x6C, 0x45, 0x82, 0x93, 0xF7, 0xA0, 0xEF, 0x2F, 0xE8, 0xB9, 0x93, 0x74, 0xD3, 0x34, 0x9C, 0x60, 0x73, 0x49, 0xE3, + 0x39, 0x7E, 0x2A, 0x9E, 0x17, 0x45, 0x6E, 0x42, 0xFB, 0x5B, 0xF0, 0x6C, 0x61, 0xB4, 0x41, 0xF5, 0x77, 0xCC, 0x8A, 0xB9, 0x3E, 0xFD, 0x7D, 0xCD, 0x6B, 0x84, 0xDB, 0xAB, 0x85, 0xA0, 0x36, 0x35, + 0x78, 0x47, 0xBC, 0xF5, 0x39, 0xEA, 0x74, 0xA5, 0x7E, 0x7D, 0xF5, 0x04, 0x84, 0x24, 0xBE, 0xAC, 0x6E, 0xD1, 0x1A, 0xE1, 0xCF, 0x05, 0xB8, 0x95, 0x1F, 0x3A, 0xE5, 0x52, 0x5B, 0x1A, 0xAF, 0x22, + 0x3C, 0xAC, 0x2D, 0xF8, 0x0E, 0x5C, 0x74, 0x7E, 0x3D, 0x9C, 0x21, 0x2B, 0xB6, 0x6D, 0x17, 0xD5, 0x12, 0x65, 0x51, 0xA8, 0x61, 0x9E, 0x3F, 0x24, 0xF5, 0x79, 0x88, 0xC4, 0xC3, 0xEB, 0x78, 0x11, + 0x80, 0xBF, 0xA1, 0x37, 0x79, 0x93, 0xCD, 0xA6, 0xD5, 0x74, 0x0D, 0x0A, 0x84, 0xDC, 0xD1, 0x87, 0x93, 0x46, 0xD4, 0xA9, 0x73, 0x5E, 0x22, 0xAB, 0x56, 0xF0, 0x14, 0x96, 0xCD, 0x4E, 0xEF, 0xE6, + 0xF8, 0xE0, 0x10, 0xD4, 0xB3, 0xF3, 0x50, 0x33, 0x89, 0xE4, 0xA8, 0x52, 0x48, 0xB3, 0x0F, 0xC4, 0x75, 0x9C, 0x38, 0x07, 0x3B, 0x1E, 0x73, 0x1A, 0x24, 0xB4, 0x91, 0xE6, 0xA7, 0xC2, 0xA8, 0x77, + 0x35, 0x0A, 0x3D, 0xBD, 0x8D, 0xDD, 0x6C, 0x0F, 0x55, 0xFC, 0x81, 0x2D, 0x5B, 0x2D, 0x54, 0xD3, 0x23, 0x7B, 0x21, 0x37, 0x10, 0xB2, 0x71, 0xB4, 0x70, 0xF2, 0x53, 0xE0, 0x85, 0x2D, 0xDA, 0x5D, + 0x84, 0xED, 0xE1, 0xEF, 0xAB, 0xAF, 0xFA, 0x6D, 0xA8, 0x63, 0xD6, 0xEE, 0x11, 0x3A, 0xBB, 0xA1, 0x48, 0xA9, 0x01, 0x8A, 0x4E, 0x5C, 0x3D, 0x8F, 0x57, 0xCA, 0x9D, 0xF0, 0x05, 0xB5, 0x9A, 0x0D, + 0x3E, 0x47, 0x40, 0x6D, 0x97, 0xE3, 0x37, 0xBB, 0x20, 0x1D, 0x78, 0x8B, 0x83, 0x29, 0xFF, 0x50, 0x66, 0x26, 0x8F, 0x4E, 0xFD, 0x51, 0x0D, 0x91, 0xB0, 0x94, 0xC0, 0xEE, 0x3D, 0x05, 0x3F, 0x2C, + 0xCB, 0x39, 0x13, 0x86, 0x34, 0xB1, 0x22, 0xD5, 0x37, 0x59, 0x14, 0x13, 0x2B, 0x31, 0x55, 0x08, 0x84, 0xFE, 0x2E, 0x9A, 0x31, 0xE5, 0x12, 0x7B, 0x2E, 0x03, 0x42, 0x7D, 0xBC, 0xF7, 0xD2, 0x55, + 0x7C, 0x5B, 0x71, 0x81, 0xBD, 0xA6, 0x83, 0x4B, 0xB9, 0x30, 0xCD, 0x3A, 0x0E, 0x0E, 0x0E, 0xAD, 0x09, 0x12, 0x0A, 0x57, 0x2B, 0xEE, 0xF7, 0x51, 0x86, 0x3A, 0xFA, 0xB3, 0x38, 0xBA, 0xC3, 0xE9, + 0xA8, 0x17, 0x9F, 0x2B, 0x5C, 0x90, 0xF0, 0xBB, 0xA6, 0xB7, 0x5F, 0xDC, 0x2A, 0xB5, 0xF7, 0x20, 0x0F, 0xEF, 0x3A, 0x65, 0xBB, 0x77, 0x64, 0x3D, 0xA0, 0xD6, 0xFE, 0xB1, 0x2D, 0x75, 0x3D, 0xF7, + 0x75, 0xEA, 0x71, 0x4E, 0x28, 0x3E, 0x0E, 0x99, 0x62, 0xA2, 0x39, 0xA0, 0x44, 0x90, 0xE7, 0xD2, 0xF9, 0x81, 0x93, 0xBB, 0xEB, 0xD6, 0xE2, 0xF5, 0x26, 0xAB, 0x0B, 0x27, 0x7E, 0x49, 0xDB, 0xC3, + 0xFA, 0x52, 0x04, 0x92, 0xD3, 0x24, 0x17, 0x28, 0x3B, 0xAB, 0xF3, 0xCE, 0xEE, 0xE0, 0xBE, 0xED, 0xBE, 0x66, 0x0C, 0x04, 0x3B, 0x19, 0x28, 0xAC, 0xDE, 0x60, 0x2F, 0x98, 0x61, 0xA5, 0x3A, 0x9E, + 0xFA, 0x9A, 0x0D, 0x9D, 0x31, 0xBB, 0xE6, 0x2B, 0xCE, 0xDE, 0x01, 0x33, 0x32, 0xF9, 0xF3, 0x3B, 0xE6, 0xA7, 0x43, 0x13, 0xFD, 0x17, 0x09, 0xAA, 0x72, 0x9B, 0xBE, 0xB7, 0xEE, 0x47, 0x91, 0xAB, + 0xA7, 0x23, 0xC2, 0x5C, 0xB3, 0xB0, 0xC6, 0x48, 0x7C, 0x62, 0x64, 0x29, 0x1E, 0xDA, 0x8F, 0x9E, 0xFF, 0x54, 0xDA, 0x37, 0x48, 0x97, 0xF9, 0x49, 0x0B, 0xF7, 0xD2, 0x05, 0x33, 0xBC, 0x29, 0x3B, + 0x9A, 0x06, 0xC4, 0x30, 0xA3, 0x37, 0x04, 0x70, 0x6C, 0x0E, 0xF0, 0x9C, 0x36, 0x95, 0xD3, 0xC0, 0x81, 0x1C, 0x05, 0xCD, 0x85, 0x5E, 0x51, 0xE9, 0xD7, 0x4E, 0x7E, 0x3C, 0xFE, 0xEB, 0x7C, 0xDA, + 0xAA, 0x89, 0x3C, 0xB9, 0x73, 0x21, 0xB2, 0x4B, 0x5B, 0xE6, 0x33, 0x3B, 0x6A, 0xBE, 0xC8, 0x11, 0xE3, 0xBC, 0xC2, 0x9C, 0xA0, 0xFA, 0xF9, 0x3B, 0x2B, 0xBD, 0x43, 0x32, 0xD9, 0xB2, 0xE7, 0xC7, + 0x89, 0xCB, 0xDE, 0x03, 0xD4, 0xFC, 0xBB, 0x47, 0x5F, 0xAD, 0x05, 0x35, 0xFE, 0xF2, 0xDD, 0xC1, 0xE2, 0x86, 0x26, 0x84, 0x19, 0x89, 0x6C, 0x41, 0x7F, 0x66, 0x5E, 0x7A, 0x02, 0x4F, 0x2C, 0xE0, + 0xAB, 0x15, 0x47, 0x57, 0x28, 0xF4, 0xE3, 0x9C, 0xAD, 0x47, 0xFE, 0x33, 0xD9, 0x10, 0x74, 0xC7, 0xB3, 0x46, 0x4E, 0xB0, 0x5E, 0x6A, 0x32, 0x3D, 0x17, 0xD7, 0x43, 0xC0, 0xE7, 0x9C, 0x9E, 0x62, + 0xA2, 0x31, 0xED, 0xF4, 0x0E, 0x75, 0x34, 0x0A, 0x23, 0x93, 0x12, 0xC4, 0xB4, 0xE5, 0xBB, 0xAC, 0x6F, 0x51, 0x1C, 0xF2, 0x54, 0x8C, 0xF8, 0x22, 0x4C, 0xCB, 0xC7, 0x3A, 0x21, 0xF8, 0xEB, 0xD3, + 0xA6, 0x64, 0x50, 0x61, 0x8D, 0x1F, 0x5B, 0x26, 0x49, 0x5F, 0xF6, 0xE8, 0x4F, 0xA1, 0xC8, 0x97, 0x82, 0xEB, 0x21, 0x1E, 0x2F, 0xB7, 0xFA, 0xD4, 0x56, 0x91, 0xBF, 0x67, 0x9E, 0x83, 0x7F, 0x88, + 0xFE, 0x5C, 0x62, 0x08, 0xAA, 0xAF, 0xAB, 0x7A, 0x42, 0x38, 0x7B, 0x0A, 0x1A, 0x48, 0xCB, 0xD5, 0x3B, 0x13, 0x81, 0x78, 0x09, 0x44, 0x5E, 0x00, 0x91, 0xBC, 0xBC, 0xEE, 0x8E, 0x9D, 0xDB, 0x41, + 0x3D, 0x13, 0x28, 0x8F, 0x53, 0xFF, 0xE6, 0xDC, 0x03, 0x9C, 0xEA, 0xE2, 0x4C, 0xE5, 0x69, 0x1E, 0xC6, 0x36, 0xBE, 0x10, 0x52, 0xEA, 0x72, 0xCD, 0x81, 0x9F, 0x5F, 0xF2, 0xF2, 0x79, 0x11, 0x5E, + 0x07, 0x82, 0x12, 0x46, 0x12, 0x2E, 0xF2, 0xAE, 0xF1, 0xC3, 0xC8, 0x49, 0x5C, 0xEA, 0xBF, 0x2B, 0x6D, 0xC3, 0xD6, 0x5C, 0x60, 0xEB, 0x2F, 0xD5, 0x69, 0x14, 0x5A, 0x63, 0xD9, 0xAB, 0xC5, 0xD4, + 0x37, 0xF7, 0xC7, 0xFC, 0x5A, 0xE2, 0x2D, 0x87, 0x87, 0x4A, 0x78, 0xDA, 0x40, 0xD5, 0x72, 0x72, 0xF7, 0xED, 0x93, 0xE0, 0xA1, 0xB4, 0x8C, 0x8B, 0xD6, 0x1A, 0x92, 0xF0, 0x8A, 0x16, 0xD0, 0x14, + 0x42, 0xF0, 0x20, 0xFB, 0xDB, 0xFF, 0xBD, 0xB1, 0x8F, 0xC5, 0xBB, 0xAD, 0x8A, 0x14, 0x21, 0x84, 0xEF, 0x9A, 0x32, 0x86, 0x13, 0xC0, 0x3D, 0x67, 0xF8, 0xBB, 0x74, 0x0F, 0x6F, 0x08, 0x3C, 0x39, + 0x3C, 0x88, 0xE8, 0x08, 0xBC, 0xC9, 0xA4, 0xCF, 0x4B, 0xEA, 0x75, 0xA1, 0x6C, 0x7A, 0x81, 0xF5, 0x1F, 0x6D, 0x9E, 0x00, 0x3E, 0xBC, 0xB8, 0xE3, 0x28, 0xA8, 0x6D, 0x7B, 0x73, 0x13, 0x3E, 0x59, + 0x66, 0x09, 0x6A, 0xFC, 0x1D, 0x1B, 0xCC, 0xCB, 0x7C, 0x84, 0xF1, 0x12, 0x35, 0x89, 0x2D, 0xEC, 0x5C, 0xFC, 0xCD, 0xF6, 0x47, 0x22, 0x49, 0x94, 0x3F, 0xB3, 0x9C, 0x7B, 0x85, 0x86, 0xC4, 0xA2, + 0xE5, 0xE8, 0x11, 0xE3, 0xFA, 0xF0, 0x68, 0xA1, 0xBC, 0xA6, 0x1F, 0x50, 0xB7, 0x59, 0xF7, 0x04, 0x2D, 0xE3, 0x4D, 0x73, 0x8F, 0x2D, 0x7C, 0x3D, 0xAB, 0x26, 0xA7, 0x39, 0x70, 0xE5, 0x08, 0x15, + 0xC5, 0x1A, 0xD7, 0x3C, 0xFC, 0xD3, 0x53, 0x0B, 0xDA, 0x1C, 0x2E, 0x91, 0x2E, 0x69, 0x4E, 0x9E, 0xE7, 0x9C, 0x09, 0x33, 0x4E, 0x4C, 0x29, 0x33, 0x9F, 0x75, 0x82, 0x30, 0x3B, 0x2E, 0x28, 0x5C, + 0x7A, 0xE8, 0x4B, 0xFF, 0x01, 0xDE, 0x1D, 0x90, 0xCA, 0xAD, 0xA4, 0x2A, 0xA4, 0xA6, 0x52, 0xC7, 0x78, 0x20, 0x75, 0xB5, 0x15, 0x14, 0xB1, 0x0C, 0x95, 0x92, 0xD3, 0x0B, 0x5A, 0x73, 0x62, 0xD9, + 0xA3, 0x2A, 0xCD, 0x26, 0x6B, 0x62, 0x86, 0x8F, 0x50, 0x73, 0x8D, 0xCA, 0xB7, 0x80, 0xCF, 0x83, 0x19, 0x83, 0x89, 0x34, 0x0F, 0x3E, 0x7A, 0x86, 0x39, 0xFE, 0x94, 0xAE, 0x0F, 0x45, 0x67, 0x29, + 0x17, 0x01, 0xEE, 0x62, 0x04, 0x58, 0x7E, 0x29, 0x53, 0x19, 0xA0, 0x05, 0x6B, 0x30, 0x4C, 0x79, 0x01, 0x19, 0x71, 0x92, 0xA8, 0xA6, 0xF4, 0xA3, 0xEA, 0x8C, 0xA3, 0x94, 0x18, 0x61, 0xE7, 0x60, + 0x1F, 0x3A, 0x89, 0xFE, 0x6F, 0x9D, 0x8C, 0x49, 0xF9, 0xBB, 0x3D, 0x95, 0xC1, 0xA0, 0x23, 0x35, 0x75, 0x98, 0x3C, 0xD7, 0xD8, 0x8F, 0x9D, 0x31, 0x5C, 0xAA, 0x9F, 0x39, 0x54, 0xB6, 0x3C, 0x6D, + 0xF2, 0x92, 0x0E, 0x16, 0xF0, 0x07, 0x6B, 0x72, 0x98, 0x35, 0x2E, 0xEF, 0x1A, 0x7E, 0x13, 0x41, 0xA3, 0x72, 0xD0, 0x76, 0x23, 0x3D, 0x01, 0x0A, 0xD4, 0xDE, 0x4C, 0x28, 0x45, 0xA6, 0xEB, 0xB6, + 0x43, 0x74, 0x5D, 0xB2, 0xDE, 0x2A, 0x02, 0xF2, 0x41, 0xD5, 0x2F, 0x16, 0xAA, 0xA8, 0x7F, 0x75, 0xC3, 0x39, 0x5C, 0x40, 0xAD, 0x3B, 0x71, 0xD3, 0x12, 0x39, 0xAD, 0x31, 0x87, 0xAF, 0xFE, 0x18, + 0xF0, 0x37, 0x0A, 0xE0, 0x83, 0x10, 0x93, 0xD9, 0x99, 0x06, 0x71, 0xE5, 0xC2, 0xAD, 0x4D, 0x99, 0xA4, 0x9C, 0x07, 0x83, 0x90, 0x7D, 0x1E, 0x1B, 0x8B, 0xF6, 0x15, 0x23, 0xFD, 0x6F, 0xC2, 0x5C, + 0x1A, 0x5C, 0xB0, 0xF1, 0xF6, 0x63, 0x16, 0x8F, 0xEA, 0x17, 0xEA, 0x6B, 0x71, 0xE0, 0xE7, 0x61, 0x83, 0x0A, 0xD7, 0xB4, 0x9F, 0xF1, 0xE7, 0x1E, 0x6D, 0xC4, 0x9D, 0xDC, 0x86, 0x5E, 0x62, 0xDF, + 0x12, 0xCE, 0x5F, 0x13, 0x84, 0x16, 0xBE, 0x79, 0x44, 0x0C, 0x72, 0x13, 0xFC, 0x2E, 0x49, 0xB5, 0x0E, 0x60, 0xA5, 0x3D, 0x50, 0xDB, 0xEA, 0xD4, 0xAD, 0x36, 0x79, 0xB0, 0xE5, 0x85, 0x45, 0xEE, + 0xA9, 0xE5, 0xE8, 0xD5, 0xDE, 0xD9, 0xC3, 0x90, 0x16, 0xE8, 0x88, 0x96, 0xDA, 0xB5, 0x9A, 0x84, 0xEB, 0xC7, 0xCC, 0xA2, 0x86, 0x67, 0xF4, 0x62, 0x20, 0x09, 0x74, 0x8F, 0x6B, 0x58, 0x54, 0xA5, + 0xE0, 0xCF, 0x07, 0x0A, 0xB6, 0x1C, 0xAC, 0xCD, 0xBF, 0x1A, 0x7E, 0xCA, 0x53, 0x1A, 0x5B, 0x5F, 0xEF, 0xDC, 0x3F, 0xF6, 0x60, 0xDD, 0xBD, 0xF0, 0x44, 0x7B, 0x70, 0x35, 0x98, 0xB7, 0x6A, 0xCD, + 0xBB, 0xE8, 0x62, 0x1E, 0x7F, 0xFC, 0xDA, 0x81, 0x08, 0xA3, 0xA1, 0x18, 0x07, 0xAC, 0x99, 0x92, 0xEC, 0x30, 0x1F, 0xDC, 0x3F, 0x65, 0x67, 0xA9, 0x99, 0x85, 0xC1, 0xA1, 0x6D, 0x9A, 0xA9, 0x28, + 0x6E, 0xAB, 0x8C, 0x65, 0xE8, 0xD1, 0x9D, 0xB0, 0x4F, 0x01, 0xD9, 0x18, 0xCA, 0x04, 0xCD, 0xA3, 0x77, 0x55, 0x95, 0x49, 0x4A, 0x4C, 0x2D, 0x53, 0x63, 0x57, 0xE5, 0x0A, 0x3C, 0x3C, 0xEC, 0x15, + 0x3F, 0xB3, 0x78, 0xDD, 0x9D, 0x2C, 0x05, 0xC1, 0xEC, 0xF8, 0x9E, 0x89, 0xA8, 0xBC, 0xC4, 0xBD, 0x27, 0x76, 0xC7, 0x9F, 0x34, 0xFA, 0x92, 0x10, 0xE9, 0xE9, 0x68, 0x1A, 0x2B, 0x37, 0x3C, 0x85, + 0x7E, 0x88, 0x30, 0xAF, 0x24, 0x60, 0x5A, 0x93, 0xA3, 0x95, 0xEB, 0xA1, 0x74, 0x4C, 0xC2, 0xF5, 0xEA, 0xA1, 0x7A, 0x42, 0x33, 0x6F, 0xE2, 0x7F, 0xDC, 0xCE, 0x42, 0xDE, 0x68, 0x92, 0xF2, 0x23, + 0x4B, 0x9E, 0x11, 0x15, 0x35, 0xF4, 0x24, 0xF0, 0xF6, 0x8D, 0xDB, 0x22, 0x0C, 0x13, 0x76, 0x24, 0x66, 0x36, 0x1E, 0x5C, 0xC9, 0xD8, 0xBE, 0x3A, 0xB7, 0xA4, 0x59, 0x76, 0xAD, 0xEF, 0x07, 0x6E, + }, + .t1_len = 1920, + .t1 = { + 0xA7, 0x2C, 0x15, 0x0F, 0xCC, 0xC9, 0xD1, 0x65, 0xCC, 0x64, 0x12, 0x64, 0xAD, 0x38, 0xCB, 0x41, 0x9B, 0xFA, 0x5E, 0x48, 0xB1, 0x9E, 0xFB, 0xA6, 0x46, 0xA1, 0x85, 0x9B, 0xB4, 0x00, 0x63, 0xA5, + 0x21, 0x2E, 0xD8, 0xFB, 0x5A, 0x60, 0x27, 0x07, 0x93, 0xBE, 0x84, 0xC6, 0xD8, 0x65, 0xA8, 0x67, 0x12, 0x76, 0xE0, 0x8E, 0xE7, 0x71, 0xD7, 0x4A, 0x35, 0xCC, 0xDE, 0x95, 0xC6, 0x1D, 0x6B, 0x19, + 0x29, 0x21, 0x0E, 0xAE, 0x6E, 0xA1, 0x03, 0xCE, 0x2A, 0x04, 0x1E, 0xAE, 0x6A, 0xA0, 0xBA, 0xED, 0x9F, 0x73, 0x6C, 0x54, 0x23, 0x8D, 0xA9, 0xFB, 0x05, 0x73, 0x6C, 0x0A, 0x79, 0x2D, 0x31, 0x06, + 0x41, 0xA0, 0xCF, 0x46, 0xC5, 0x02, 0xDA, 0x44, 0x98, 0x1C, 0x7C, 0x85, 0xDA, 0x6B, 0xC4, 0x4A, 0x39, 0xD6, 0x0F, 0xCC, 0x79, 0xAA, 0xE5, 0x2B, 0x79, 0x43, 0xBC, 0x34, 0x91, 0x58, 0x07, 0xA9, + 0x61, 0x13, 0x40, 0x9A, 0xF8, 0x4C, 0x95, 0x6C, 0xBF, 0x7E, 0x8F, 0x1E, 0x44, 0xCF, 0x8E, 0x37, 0x51, 0x4A, 0x1C, 0xC7, 0x78, 0x01, 0xA2, 0x07, 0x0A, 0x3B, 0xBE, 0xC6, 0xA6, 0x7F, 0xD5, 0xBF, + 0xB6, 0x67, 0x68, 0x16, 0x76, 0x44, 0xE5, 0x7C, 0x03, 0x69, 0x0C, 0x12, 0xA4, 0xA1, 0x8B, 0xBD, 0xEA, 0x35, 0xFB, 0x3A, 0x2D, 0x61, 0x9A, 0x55, 0xBE, 0x10, 0xCB, 0x9B, 0x79, 0xA8, 0x4B, 0x10, + 0xD8, 0xE6, 0xD3, 0x85, 0x56, 0x46, 0x5B, 0x5A, 0x10, 0x57, 0x69, 0x66, 0xF1, 0xD4, 0xCC, 0x4A, 0x1F, 0x4E, 0x36, 0x2A, 0xD5, 0x84, 0x36, 0x3F, 0xDA, 0xF0, 0xAD, 0x0B, 0xF1, 0x79, 0x29, 0x0D, + 0x57, 0xC3, 0xD8, 0xD2, 0x74, 0x01, 0xB0, 0xF2, 0x14, 0x18, 0x3A, 0x7C, 0x36, 0x9A, 0x06, 0x53, 0xF5, 0x10, 0x57, 0xE7, 0x6F, 0x6E, 0x8B, 0x68, 0x34, 0x2D, 0x59, 0x2E, 0x2B, 0xA1, 0xA1, 0xDB, + 0x44, 0x40, 0x98, 0x0C, 0x1D, 0x61, 0x6E, 0x8B, 0xF5, 0xF1, 0x5A, 0x18, 0xC3, 0x1E, 0xDD, 0xAC, 0xC2, 0x9A, 0xC5, 0x80, 0x43, 0x8E, 0x5A, 0x64, 0x52, 0x68, 0x89, 0x19, 0x1F, 0x01, 0x99, 0xE1, + 0x98, 0x84, 0xC4, 0xA6, 0xDA, 0xE8, 0x92, 0x10, 0x10, 0xAE, 0x79, 0xC0, 0xA4, 0x19, 0xBC, 0x3B, 0x0E, 0x62, 0x2E, 0xE0, 0xAD, 0xC0, 0xFE, 0xF4, 0xFD, 0x43, 0xB7, 0xBD, 0x4B, 0x80, 0x0D, 0xE3, + 0x00, 0xA3, 0xD7, 0xD2, 0xDD, 0x26, 0xF3, 0x34, 0xFE, 0x9C, 0x5B, 0x14, 0xF8, 0xBC, 0xA4, 0x09, 0x9E, 0x6F, 0x9D, 0xAE, 0x55, 0xB8, 0xF6, 0xC4, 0xB1, 0x17, 0x45, 0x9E, 0xE6, 0xD7, 0xEE, 0xEF, + 0xB1, 0x03, 0x95, 0x69, 0x29, 0x7C, 0x14, 0x7B, 0xF0, 0x12, 0xC5, 0x0C, 0xFA, 0xBC, 0x34, 0x13, 0x48, 0x39, 0xEF, 0x54, 0x57, 0xBF, 0xFB, 0x88, 0x3F, 0x3C, 0x01, 0xC7, 0x5B, 0xA9, 0x4A, 0x47, + 0xE2, 0xDC, 0xAE, 0x22, 0xC5, 0xB7, 0xF3, 0x9C, 0x16, 0xA2, 0x1A, 0x9D, 0x27, 0xF6, 0x88, 0x84, 0x30, 0xCC, 0x25, 0x50, 0xF8, 0x6D, 0xA8, 0x04, 0xAA, 0x1E, 0x29, 0xF1, 0x55, 0x0A, 0xD8, 0x8F, + 0xC4, 0x99, 0xE2, 0x07, 0x0D, 0xCB, 0xD9, 0xAB, 0xFA, 0x39, 0x10, 0x4D, 0x76, 0x65, 0xA9, 0xB8, 0xC5, 0x8B, 0xE9, 0x8B, 0x41, 0x83, 0xC7, 0xF1, 0xA6, 0x6E, 0x55, 0x7C, 0x60, 0x91, 0x83, 0xE5, + 0xF2, 0x02, 0x09, 0x05, 0x16, 0xAA, 0xBF, 0x8D, 0x31, 0x07, 0xE2, 0x49, 0x9B, 0x29, 0xD3, 0x59, 0x3D, 0xE2, 0xBA, 0x9D, 0x16, 0xB5, 0x39, 0xD0, 0xC1, 0x51, 0xF7, 0xF0, 0xE1, 0x96, 0xFD, 0xF5, + 0x7A, 0xE6, 0xF3, 0xB4, 0xE5, 0x8A, 0xE9, 0xB9, 0xA0, 0x3A, 0xEC, 0x96, 0x70, 0x0B, 0xE5, 0xBF, 0x52, 0x4E, 0xA4, 0x48, 0xEC, 0xAE, 0x16, 0x82, 0x5C, 0x29, 0xA9, 0xE1, 0x6E, 0x38, 0xC3, 0x79, + 0x24, 0xEB, 0x7E, 0xD5, 0xE8, 0x33, 0x87, 0x2E, 0x0D, 0x09, 0x9C, 0x96, 0x15, 0x4C, 0xBC, 0x53, 0xF0, 0xF1, 0x9C, 0x50, 0xB6, 0x70, 0xDD, 0xE7, 0xC9, 0x72, 0x23, 0x35, 0x74, 0xC6, 0x5A, 0xA0, + 0x00, 0x67, 0x32, 0x99, 0x36, 0x5B, 0x43, 0x70, 0x56, 0xCB, 0xDE, 0x78, 0xF6, 0x88, 0x78, 0x6E, 0xB9, 0xDD, 0x75, 0x32, 0x54, 0xA2, 0x30, 0x15, 0xA5, 0xE5, 0x4B, 0xE0, 0x4F, 0xB7, 0xA6, 0x08, + 0xB6, 0xE6, 0x89, 0xBB, 0x4F, 0x2C, 0x72, 0xF0, 0x99, 0x37, 0x87, 0x9E, 0xA7, 0x9B, 0x0E, 0x0E, 0xC0, 0x0A, 0xB8, 0xD6, 0x6C, 0xC7, 0x87, 0xE4, 0xD9, 0x67, 0x59, 0x1D, 0x6B, 0xE1, 0xEB, 0x98, + 0x44, 0x11, 0x2A, 0x52, 0x7E, 0x9D, 0x1F, 0xA5, 0xEE, 0x7F, 0x95, 0x38, 0xB7, 0x54, 0xFD, 0xF2, 0x19, 0x96, 0xB1, 0x45, 0xBA, 0xD0, 0x1C, 0xD7, 0x3D, 0x04, 0x2D, 0x2B, 0xE3, 0x70, 0x15, 0x3D, + 0x5E, 0xD5, 0x3E, 0x5E, 0xD4, 0x33, 0x32, 0x3A, 0x8D, 0xB0, 0xBF, 0x83, 0xF0, 0x3F, 0x8B, 0x96, 0xC4, 0x2C, 0xD9, 0xC9, 0xA3, 0x81, 0x20, 0x8F, 0xFD, 0xA0, 0x58, 0xA4, 0xA0, 0xC2, 0xF4, 0xA3, + 0x7E, 0x98, 0x53, 0x09, 0xE8, 0xD0, 0x80, 0xB7, 0x35, 0x32, 0x62, 0xE0, 0x6B, 0xF6, 0x3F, 0x82, 0xE7, 0xAD, 0x07, 0xBF, 0x06, 0x8B, 0xC0, 0x93, 0xB6, 0x85, 0x04, 0x4C, 0x4F, 0x41, 0xF9, 0x64, + 0xCA, 0x1B, 0xED, 0x2F, 0x1F, 0xD8, 0x54, 0xD6, 0x13, 0x13, 0x9B, 0x1F, 0xBD, 0xE1, 0x6B, 0xAD, 0x79, 0x93, 0x0A, 0xEE, 0xEE, 0x86, 0x58, 0xAE, 0x71, 0xD1, 0xB4, 0xB9, 0x65, 0x95, 0xE4, 0xFC, + 0xED, 0x1A, 0x2C, 0x29, 0x1E, 0xC7, 0x26, 0x10, 0x70, 0x0C, 0xA0, 0xE3, 0x69, 0x24, 0x84, 0xEA, 0x07, 0xCE, 0xE7, 0x2C, 0x9B, 0x8A, 0x2E, 0x5A, 0x97, 0x12, 0x93, 0xBE, 0x38, 0x2D, 0x2A, 0xB0, + 0xFE, 0x1F, 0x3F, 0x36, 0x54, 0x19, 0x22, 0xE1, 0x03, 0x0A, 0xB0, 0x65, 0xD0, 0x76, 0x64, 0x53, 0x96, 0xD7, 0x12, 0x9F, 0xE7, 0xEF, 0xBB, 0x73, 0x75, 0x39, 0x02, 0x27, 0x18, 0x9B, 0xED, 0xBD, + 0x3C, 0x83, 0xB1, 0x61, 0x7E, 0x5A, 0x2A, 0x0B, 0x06, 0xFA, 0xEA, 0x43, 0x9A, 0x1D, 0xE1, 0xCD, 0x7E, 0x9C, 0xB4, 0x0A, 0xD8, 0xB2, 0x97, 0x68, 0x8C, 0x0C, 0xF8, 0x25, 0x47, 0xD0, 0xB6, 0x5C, + 0x6A, 0x9D, 0x2A, 0x7F, 0xE3, 0x96, 0x78, 0xB3, 0xC9, 0x6B, 0xE4, 0xD0, 0xE6, 0xD0, 0x1A, 0x51, 0xF6, 0xA2, 0x19, 0x80, 0xB0, 0x0E, 0x43, 0x16, 0x7F, 0xCD, 0x36, 0x6F, 0x00, 0x6D, 0x90, 0x53, + 0xA6, 0x1A, 0x9A, 0xA1, 0xFE, 0x19, 0x6B, 0xAC, 0x97, 0xA4, 0xF5, 0xD4, 0x3F, 0x5A, 0x99, 0xF2, 0xB5, 0x72, 0x18, 0xA1, 0x9C, 0x07, 0xAF, 0xE6, 0x31, 0xC0, 0x55, 0xD3, 0x6F, 0x8F, 0x23, 0x58, + 0xD0, 0x69, 0xC7, 0x9C, 0xC6, 0x46, 0xAE, 0x4E, 0x30, 0x41, 0x4F, 0xC6, 0x0A, 0x8D, 0x0E, 0xC0, 0x45, 0xED, 0x10, 0xC2, 0x74, 0x41, 0xB4, 0x45, 0x78, 0x58, 0x40, 0x63, 0xE7, 0x26, 0xA9, 0x38, + 0xB1, 0xB0, 0x9F, 0x22, 0x09, 0xC8, 0x10, 0x5C, 0xCC, 0xF9, 0xA1, 0x90, 0x82, 0x9F, 0xE4, 0x7F, 0xED, 0x26, 0x4A, 0xCF, 0xBE, 0xC7, 0x8F, 0x8E, 0x8B, 0x1A, 0x8E, 0x10, 0x28, 0xB0, 0xDD, 0x2C, + 0x59, 0xBF, 0xEF, 0xE2, 0x47, 0xDC, 0xCD, 0x85, 0x98, 0x54, 0x42, 0x13, 0xA3, 0x6A, 0x5F, 0x19, 0x05, 0xC8, 0x7D, 0x96, 0xAC, 0x8C, 0xC1, 0x2D, 0x37, 0xAC, 0xE5, 0x96, 0x97, 0xA1, 0x39, 0xD3, + 0x53, 0x69, 0x7E, 0x1E, 0xEA, 0xB1, 0x24, 0x1C, 0x6D, 0xFA, 0x70, 0x76, 0x21, 0xEC, 0x47, 0x51, 0x13, 0xA5, 0x26, 0xD9, 0x11, 0x1F, 0xC9, 0xB5, 0x95, 0x7A, 0xA5, 0x44, 0xD6, 0x1D, 0x9F, 0xB7, + 0x60, 0xAD, 0xE4, 0xA2, 0x86, 0xDF, 0x28, 0x5B, 0xBD, 0x1A, 0xE6, 0x48, 0x63, 0xF7, 0x04, 0xEA, 0x46, 0x44, 0xD9, 0xCB, 0x2E, 0x77, 0xD2, 0x23, 0x80, 0x01, 0xE7, 0xC8, 0x96, 0x1E, 0xFA, 0x19, + 0x54, 0xEC, 0xE6, 0xEC, 0x59, 0xA4, 0x75, 0x8B, 0x87, 0xC3, 0x18, 0x81, 0x9F, 0x86, 0x5D, 0x73, 0x54, 0xC1, 0xD5, 0xDF, 0xCF, 0xDE, 0x5B, 0x41, 0xF4, 0xEE, 0xA9, 0x30, 0xA7, 0xFE, 0x40, 0x80, + 0x8D, 0xE9, 0x50, 0xBD, 0x88, 0x19, 0x96, 0xC6, 0xA3, 0x33, 0xAF, 0x6F, 0xB0, 0x90, 0xDD, 0x2E, 0xF3, 0x94, 0x5F, 0x9C, 0xCC, 0x0A, 0x60, 0x17, 0xA3, 0x6C, 0xE4, 0x84, 0x47, 0xFD, 0xD9, 0x61, + 0xE4, 0xB1, 0x7D, 0xD0, 0x2B, 0x4A, 0x3A, 0xA7, 0xB5, 0xE9, 0x8A, 0x86, 0xEA, 0x97, 0x3E, 0x66, 0x97, 0xCA, 0x03, 0x44, 0xCB, 0xFC, 0xB5, 0xF2, 0xD9, 0xAE, 0xE9, 0xEF, 0x6E, 0xF6, 0xF5, 0x7F, + 0x62, 0x72, 0x88, 0x6D, 0x67, 0x11, 0x23, 0x46, 0xB2, 0x56, 0xBF, 0xF7, 0xA5, 0xA1, 0x5B, 0x6E, 0x31, 0x07, 0x5D, 0x68, 0xA9, 0xBD, 0x73, 0x8B, 0x16, 0x0D, 0x9D, 0x2B, 0x06, 0x9B, 0x45, 0xB2, + 0xC5, 0x8C, 0xA7, 0x01, 0x65, 0xF6, 0x00, 0x9F, 0xEF, 0xE9, 0xFB, 0xE6, 0xB7, 0xD2, 0x51, 0x95, 0x1C, 0xF8, 0x16, 0x23, 0x3D, 0x0C, 0x0B, 0xE5, 0x99, 0xE6, 0xA6, 0x9D, 0xDD, 0xAD, 0x52, 0xD2, + 0x15, 0xE1, 0xBA, 0xB1, 0xF7, 0xF8, 0x54, 0x45, 0x38, 0x39, 0xA0, 0x07, 0x0A, 0xC4, 0x28, 0x2A, 0x48, 0x75, 0xF3, 0x85, 0xF7, 0x2C, 0x7A, 0x9D, 0xE6, 0x92, 0x1B, 0xCA, 0xD9, 0xE1, 0x73, 0xE1, + 0x3D, 0x33, 0xB6, 0xA0, 0x94, 0xF0, 0xE4, 0x66, 0xA0, 0xE4, 0xC9, 0x49, 0x5E, 0xA0, 0x75, 0x43, 0xE1, 0x2D, 0x9F, 0x95, 0x20, 0x96, 0xDB, 0xCD, 0xA1, 0x57, 0x5B, 0xC1, 0x0C, 0xCC, 0xF0, 0xAF, + 0x60, 0xCD, 0x4A, 0x75, 0x7A, 0xF9, 0x0E, 0x4E, 0xCD, 0x08, 0x32, 0x26, 0xE8, 0x31, 0x87, 0x09, 0x68, 0x5D, 0x3C, 0x26, 0xB6, 0xF9, 0x51, 0x5B, 0x0E, 0x08, 0xFC, 0x51, 0xF0, 0x90, 0x6D, 0x73, + 0x30, 0x50, 0x4C, 0xD4, 0x13, 0x6F, 0xF6, 0x2D, 0xC5, 0x6A, 0xB2, 0x3B, 0xB5, 0xAB, 0x4B, 0x4D, 0x71, 0x3F, 0xCD, 0x4C, 0xB6, 0x84, 0x03, 0x6A, 0x74, 0x36, 0x6B, 0xBC, 0x67, 0x46, 0x52, 0xAC, + 0x6E, 0xDD, 0x0B, 0x7B, 0xB2, 0xF1, 0x5D, 0x70, 0xF0, 0x86, 0x85, 0x1B, 0x94, 0x65, 0x24, 0x71, 0x52, 0x7C, 0xA2, 0x7F, 0x06, 0x74, 0x45, 0x9A, 0x7B, 0x00, 0x8B, 0x35, 0x53, 0x9E, 0xC2, 0x4F, + 0x65, 0x16, 0x03, 0x4F, 0xCF, 0x6F, 0x84, 0xCD, 0x65, 0xD2, 0xA5, 0x06, 0x26, 0xE0, 0xD6, 0x62, 0xBC, 0x02, 0x9F, 0x52, 0x54, 0xFB, 0x20, 0xAD, 0x8C, 0x92, 0xB2, 0xBB, 0xE2, 0x75, 0xBB, 0x69, + 0x67, 0xF4, 0x18, 0x22, 0xA9, 0x21, 0x6C, 0x30, 0x6C, 0x2A, 0x32, 0x7E, 0x13, 0xEF, 0x14, 0xC4, 0x65, 0x1D, 0x0F, 0x42, 0x5B, 0xDD, 0xD3, 0x07, 0x08, 0x1C, 0xDB, 0x6D, 0xC7, 0xB4, 0x0C, 0xF6, + 0xB2, 0x73, 0xFC, 0xEE, 0x1D, 0x78, 0x19, 0x6C, 0xE7, 0xAF, 0x83, 0xEB, 0x85, 0x03, 0x9A, 0x00, 0x17, 0x86, 0x2F, 0xF3, 0x04, 0x8B, 0xB6, 0x5B, 0xBD, 0xCF, 0x5B, 0x4D, 0x3E, 0x25, 0x3C, 0x1B, + 0x3F, 0x52, 0x2E, 0x33, 0x74, 0x74, 0x5E, 0x35, 0xFB, 0x32, 0x20, 0x8D, 0xCC, 0x5C, 0x25, 0x6A, 0x5C, 0x87, 0xF4, 0x03, 0x34, 0x41, 0xB7, 0x6F, 0x6B, 0x4C, 0x11, 0xE2, 0x84, 0xB0, 0xD5, 0x3B, + 0xB5, 0x03, 0x64, 0x1D, 0x8B, 0x4C, 0x41, 0xBE, 0x7B, 0xE2, 0x17, 0xDD, 0xCC, 0xCA, 0xBE, 0xBB, 0xDE, 0x2C, 0x48, 0xCE, 0x37, 0x55, 0x0F, 0x8A, 0xA1, 0x7F, 0x41, 0x7E, 0x8F, 0x6D, 0x76, 0x58, + 0x0C, 0x69, 0x03, 0x0F, 0xE1, 0x7E, 0x5C, 0x16, 0x6B, 0xC5, 0x11, 0x32, 0xBB, 0xC5, 0x26, 0x4C, 0x87, 0x64, 0x9E, 0x2F, 0xA3, 0x56, 0xD6, 0xF8, 0x95, 0x78, 0x5F, 0x2D, 0xFC, 0x46, 0x77, 0xA6, + 0xEA, 0xF7, 0xBA, 0xE8, 0x68, 0xB0, 0x90, 0xD9, 0x0C, 0xCF, 0x11, 0xEA, 0x20, 0x97, 0x93, 0x3D, 0x5F, 0x19, 0x9A, 0x9A, 0x32, 0x4B, 0xF9, 0x7A, 0xDE, 0xE6, 0x8A, 0x04, 0x07, 0x13, 0x41, 0x66, + 0xB1, 0x0C, 0x5E, 0x52, 0x31, 0x32, 0xBB, 0x93, 0xDE, 0x89, 0xB3, 0x86, 0xE4, 0xB2, 0x70, 0x98, 0x0C, 0x35, 0x13, 0x2B, 0x67, 0x7C, 0xE9, 0xD9, 0xF2, 0x50, 0x80, 0x2E, 0x4C, 0x77, 0x9C, 0x44, + 0x15, 0x3A, 0x3A, 0x4F, 0xD0, 0x86, 0x64, 0x10, 0x2F, 0x5A, 0xE9, 0x9C, 0xE9, 0xF0, 0x40, 0x38, 0x35, 0x00, 0xE9, 0x99, 0x65, 0x54, 0x04, 0x7A, 0x90, 0xDC, 0x24, 0xB2, 0x2F, 0x77, 0xD1, 0x99, + 0xCB, 0xAD, 0xD9, 0xC4, 0xA5, 0xC4, 0xF0, 0x10, 0x60, 0x80, 0xDE, 0xE3, 0x6F, 0xBE, 0x4A, 0x1F, 0xBE, 0x3E, 0x71, 0x68, 0xB5, 0x4F, 0x88, 0xD5, 0xEF, 0xE7, 0x5E, 0x07, 0x05, 0xE7, 0xF2, 0xBB, + 0xD5, 0xF0, 0x1C, 0xA8, 0x8A, 0x3A, 0x5C, 0xAD, 0x44, 0x16, 0x26, 0x34, 0x8B, 0xE4, 0xF6, 0x5B, 0xED, 0xC6, 0x5D, 0xA4, 0xF9, 0x21, 0x8A, 0xCE, 0xBF, 0x93, 0x9D, 0x48, 0xD5, 0x3D, 0x54, 0x01, + 0xF4, 0x60, 0x91, 0x77, 0xCE, 0xF8, 0x3B, 0x1D, 0xBD, 0xCF, 0x5E, 0xE2, 0x6B, 0xB5, 0x47, 0x62, 0x37, 0x1D, 0xBA, 0xCA, 0x8E, 0x4D, 0x17, 0xF9, 0xE0, 0xBE, 0x96, 0x11, 0x15, 0xA7, 0x15, 0x15, + 0x36, 0x8B, 0xDC, 0x16, 0xF5, 0xB8, 0x57, 0xF7, 0xCD, 0xDE, 0xB5, 0xE7, 0x8A, 0xFB, 0x58, 0x6F, 0x19, 0x72, 0x5B, 0xD6, 0xEC, 0xA4, 0xA7, 0x76, 0xB2, 0xE7, 0x13, 0x1F, 0x66, 0x19, 0x9E, 0xD5, + 0x5A, 0x68, 0x91, 0xA6, 0x32, 0x6A, 0xC9, 0x3C, 0xBF, 0x2C, 0xA2, 0x24, 0xB4, 0xB8, 0x04, 0xC4, 0x89, 0x3C, 0x97, 0x7C, 0xFB, 0x75, 0xBA, 0xDC, 0xCF, 0x56, 0x7B, 0x49, 0x05, 0x8C, 0x60, 0xF5, + 0x49, 0x52, 0x22, 0x64, 0xDC, 0x5E, 0xF9, 0xCA, 0x9D, 0xA5, 0x30, 0x0D, 0x10, 0xC5, 0x5A, 0x3E, 0x0B, 0x91, 0x68, 0x1C, 0x35, 0xB8, 0x44, 0xEC, 0x78, 0xAC, 0x03, 0x42, 0x95, 0x71, 0x61, 0x36, + 0x9F, 0x19, 0x2F, 0xC6, 0xB6, 0xE6, 0x25, 0xF1, 0xF8, 0xC0, 0x59, 0x73, 0x0A, 0x99, 0xD1, 0xA4, 0x73, 0xD3, 0x89, 0x2B, 0x95, 0x5F, 0xAC, 0xCF, 0x92, 0x66, 0x02, 0x32, 0xB0, 0x29, 0x6F, 0xA6, + 0xE9, 0xCA, 0xC5, 0x6C, 0xCB, 0xB2, 0xE9, 0xD9, 0xC6, 0x55, 0x30, 0x14, 0x5A, 0xFB, 0x13, 0x41, 0xB8, 0x73, 0x75, 0xB5, 0x15, 0x88, 0x93, 0xB9, 0x3A, 0xE9, 0x9E, 0x39, 0x2B, 0xFE, 0x69, 0x40, + }, + .pkcs8_len = 0, + .spki_len = 0, + .msg_len = 66, + .msg = { + 0x22, 0x5D, 0x5C, 0xE2, 0xCE, 0xAC, 0x61, 0x93, 0x0A, 0x07, 0x50, 0x3F, 0xB5, 0x9F, 0x7C, 0x2F, 0x93, 0x6A, 0x3E, 0x07, 0x54, 0x81, 0xDA, 0x3C, 0xA2, 0x99, 0xA8, 0x0F, 0x8C, 0x5D, 0xF9, 0x22, + 0x3A, 0x07, 0x3E, 0x7B, 0x90, 0xE0, 0x2E, 0xBF, 0x98, 0xCA, 0x22, 0x27, 0xEB, 0xA3, 0x8C, 0x1A, 0xB2, 0x56, 0x82, 0x09, 0xE4, 0x6D, 0xBA, 0x96, 0x18, 0x69, 0xC6, 0xF8, 0x39, 0x83, 0xB1, 0x7D, + 0xCD, 0x49, + }, + .sig_len = 3293, + .sig = { + 0xBE, 0xE5, 0x9E, 0x79, 0x09, 0xC2, 0xA0, 0xAB, 0xBD, 0xC3, 0xF9, 0xD0, 0x7D, 0x40, 0x5A, 0x96, 0x2E, 0x64, 0x2A, 0x1F, 0x1C, 0x1F, 0xD0, 0xB7, 0xAD, 0x6D, 0x99, 0x99, 0x0C, 0xE6, 0x9D, 0x5D, + 0x8D, 0x2D, 0xF8, 0x9B, 0xB9, 0x6F, 0xF9, 0xB5, 0xB6, 0xFC, 0xA6, 0x48, 0xDF, 0x08, 0x56, 0x45, 0x7B, 0x91, 0x9B, 0x38, 0x13, 0x16, 0x35, 0xDD, 0x81, 0x4A, 0x7A, 0xA8, 0xB0, 0xB9, 0x47, 0xDD, + 0x70, 0xA6, 0x7E, 0x49, 0x73, 0xFE, 0x33, 0xE1, 0xE0, 0x02, 0x22, 0x59, 0x7C, 0x2B, 0xE8, 0xF8, 0x67, 0x80, 0x12, 0x26, 0x41, 0x53, 0xAA, 0xCA, 0x64, 0x80, 0xC5, 0xF1, 0x8C, 0xA3, 0xC0, 0x50, + 0x45, 0x0D, 0x42, 0xD9, 0xE5, 0x6B, 0x9B, 0x5E, 0x76, 0xF3, 0xAE, 0x3B, 0xDB, 0x58, 0x95, 0x81, 0xC4, 0xAC, 0xF8, 0x10, 0x75, 0x35, 0xB1, 0xFE, 0x7D, 0x49, 0x42, 0xCB, 0xBC, 0xDF, 0xBA, 0x4E, + 0xC1, 0xAF, 0xBA, 0xA4, 0x60, 0x95, 0x61, 0x95, 0xB1, 0x72, 0x93, 0xDC, 0x18, 0xCF, 0x0A, 0x3B, 0x43, 0x6E, 0xC4, 0x74, 0x60, 0x0B, 0xE1, 0xB6, 0xE6, 0x1A, 0xE6, 0x1C, 0x4F, 0x9B, 0x2F, 0xB1, + 0x22, 0x98, 0x36, 0x2D, 0x9E, 0xF0, 0x1E, 0xC6, 0x8A, 0x46, 0x22, 0x95, 0x7B, 0x96, 0x4C, 0x30, 0x56, 0x29, 0xC4, 0x26, 0x34, 0xCF, 0x88, 0x47, 0xA7, 0x58, 0x12, 0x09, 0x41, 0x8E, 0x24, 0x58, + 0x90, 0x6E, 0x15, 0xC8, 0xE3, 0x0E, 0x74, 0xD8, 0xC8, 0x74, 0xD8, 0x5D, 0xC6, 0x3E, 0xB1, 0x1A, 0x96, 0x07, 0x57, 0xAD, 0xD9, 0xED, 0xAA, 0x6D, 0x9A, 0xF8, 0xB2, 0xE3, 0x55, 0x10, 0x22, 0xB2, + 0x34, 0x26, 0x31, 0x9D, 0x37, 0xAD, 0xF1, 0x92, 0xC2, 0x4E, 0xFD, 0xCF, 0x8D, 0x95, 0xEF, 0xE8, 0x6C, 0x16, 0x45, 0x9A, 0xAC, 0xA0, 0xDF, 0x6A, 0xE4, 0x14, 0xCD, 0x93, 0xB7, 0x0D, 0x57, 0xE7, + 0xA7, 0x64, 0x4C, 0x48, 0x91, 0xC0, 0x87, 0x96, 0xB3, 0xFD, 0x59, 0x2E, 0x51, 0xB1, 0xFA, 0x59, 0x1F, 0xD7, 0x1B, 0xC4, 0xFE, 0xC3, 0xB9, 0xA8, 0xDF, 0x5A, 0x92, 0x53, 0x57, 0xDF, 0x46, 0x82, + 0xA4, 0x58, 0x3F, 0x78, 0x8B, 0x61, 0x9D, 0x6D, 0xEC, 0x6A, 0xCD, 0x4A, 0x5A, 0x17, 0xE8, 0xF4, 0x16, 0x53, 0x96, 0x2A, 0x83, 0xB4, 0x5D, 0xA6, 0xC0, 0x87, 0xC8, 0xBE, 0xF1, 0x6E, 0x95, 0xD2, + 0xD4, 0x34, 0x38, 0x52, 0x7E, 0x92, 0x73, 0x64, 0x5E, 0x22, 0x58, 0x4E, 0xE6, 0xAD, 0xCE, 0xA4, 0xE2, 0x51, 0xCD, 0x79, 0xA0, 0x78, 0xEF, 0xF9, 0xC2, 0x9C, 0xE4, 0x52, 0xEA, 0xBA, 0x9C, 0xE3, + 0x21, 0x25, 0x71, 0x9F, 0xBE, 0xE5, 0xF9, 0xA9, 0x01, 0x31, 0xDF, 0x0C, 0xFD, 0xCA, 0x49, 0x49, 0x6A, 0xDC, 0x48, 0x5E, 0x8B, 0x08, 0xF3, 0x0F, 0xC3, 0xED, 0x0A, 0x29, 0x2A, 0x15, 0x4E, 0x3E, + 0x3C, 0x89, 0x34, 0x4A, 0xB9, 0xBA, 0x4E, 0x33, 0x23, 0xDD, 0x16, 0xC6, 0xEE, 0xD1, 0x84, 0xFE, 0x25, 0xE5, 0x62, 0xAC, 0x6B, 0xF7, 0xD0, 0x44, 0x15, 0xEA, 0x37, 0x0B, 0x72, 0xE5, 0x1A, 0x44, + 0x9E, 0xE6, 0xB5, 0x81, 0x83, 0x25, 0x0C, 0xDC, 0xB2, 0x27, 0x20, 0x5E, 0xCE, 0x5E, 0x9F, 0x63, 0x1D, 0xFE, 0xDE, 0x70, 0x2C, 0xE4, 0xEC, 0x66, 0xF8, 0x3B, 0xA7, 0x9D, 0x3F, 0xB4, 0x42, 0x2A, + 0xD6, 0xF4, 0x3B, 0x64, 0x41, 0x18, 0x95, 0x3E, 0x56, 0x47, 0x5D, 0x2D, 0x0C, 0x3A, 0x92, 0x51, 0xD9, 0x6A, 0x98, 0x67, 0xD8, 0x04, 0x9D, 0xF2, 0x17, 0x72, 0x4B, 0x42, 0x0F, 0xC3, 0xA4, 0xDF, + 0x2B, 0x86, 0x78, 0xD2, 0x90, 0x2B, 0x32, 0xD4, 0x4D, 0x93, 0x3F, 0xC5, 0x6C, 0x3F, 0x80, 0x22, 0xF8, 0x7A, 0xFD, 0xA3, 0x76, 0x89, 0x10, 0x5C, 0xAC, 0x8E, 0xCB, 0x2C, 0x8C, 0x2A, 0x92, 0x8B, + 0xDB, 0xAE, 0x81, 0x01, 0xE3, 0x44, 0x9F, 0x61, 0x36, 0xB0, 0x53, 0xAA, 0xA2, 0x0C, 0x14, 0x0B, 0xD9, 0x20, 0xB9, 0xBB, 0x67, 0x65, 0x5E, 0xE7, 0x9B, 0xC4, 0xE2, 0x63, 0x6C, 0xB0, 0xCA, 0x4A, + 0x7E, 0xFE, 0x39, 0x72, 0xF9, 0xA0, 0xC6, 0xCF, 0x16, 0xAD, 0x16, 0x33, 0xCE, 0x51, 0xF2, 0xC5, 0x4A, 0x77, 0x12, 0xE6, 0x9D, 0x57, 0x7A, 0x20, 0x83, 0x4C, 0x4A, 0xD1, 0xCC, 0xE4, 0xE3, 0xF8, + 0xC1, 0xAB, 0x65, 0xC1, 0x54, 0x8B, 0x00, 0x02, 0x67, 0x28, 0xE5, 0x7D, 0x42, 0xA2, 0x94, 0x28, 0x82, 0xB2, 0x4B, 0x45, 0x94, 0x44, 0xEB, 0x43, 0x2B, 0x89, 0x5A, 0xCA, 0x2A, 0x71, 0xA6, 0x2A, + 0x34, 0x92, 0x7E, 0x56, 0x75, 0x81, 0xD8, 0xBA, 0x2A, 0x1E, 0x52, 0xF0, 0xAE, 0xEE, 0xE1, 0xB0, 0x86, 0x4B, 0xF3, 0x7D, 0x7A, 0xE5, 0xCA, 0x2D, 0x2F, 0x15, 0x2E, 0x73, 0x89, 0x22, 0x4C, 0xA7, + 0xF9, 0x13, 0x2B, 0x89, 0x39, 0xE1, 0xB1, 0xCC, 0xBF, 0xC0, 0x3B, 0x2B, 0xE9, 0xA4, 0x60, 0xCF, 0xC7, 0xDC, 0x5A, 0xA5, 0x04, 0xF7, 0xFC, 0xD9, 0x46, 0xDC, 0xE5, 0xC6, 0x39, 0x9D, 0xA6, 0xC0, + 0xC8, 0xD8, 0xCC, 0x8B, 0x0C, 0x0B, 0x30, 0x73, 0x6C, 0x63, 0x10, 0x25, 0xA6, 0xA3, 0xA9, 0xE2, 0xD9, 0x4C, 0xDC, 0xBD, 0x3C, 0xE7, 0xA6, 0x8D, 0x7F, 0xFD, 0xEE, 0xAA, 0x45, 0x9B, 0x10, 0x4B, + 0xB7, 0x30, 0xED, 0x7C, 0x9E, 0x87, 0xBB, 0x02, 0xE8, 0x9D, 0xEE, 0x4F, 0x91, 0x5F, 0xD2, 0xE3, 0x1B, 0xF4, 0x18, 0xA1, 0x55, 0x02, 0xA4, 0xB2, 0xE4, 0x26, 0xED, 0xEA, 0x8A, 0x14, 0x26, 0x90, + 0xA4, 0x5E, 0xDA, 0xB3, 0xE6, 0x37, 0xF7, 0x97, 0xE7, 0xA7, 0x86, 0xB8, 0xA8, 0xE9, 0x0E, 0x9E, 0xE0, 0xD5, 0x78, 0x1E, 0xCD, 0x16, 0x91, 0x1F, 0xB0, 0xF4, 0xEB, 0x5B, 0x0C, 0x70, 0x74, 0x98, + 0xFE, 0x7D, 0x8C, 0x2A, 0xE6, 0x73, 0xA3, 0x33, 0x4A, 0xFB, 0x95, 0xAC, 0x6B, 0x18, 0x5A, 0xF3, 0x6F, 0xA1, 0x87, 0x74, 0x93, 0x8B, 0xA6, 0x56, 0xB2, 0x2F, 0xDC, 0x9A, 0xCB, 0xCF, 0xBF, 0x95, + 0xD1, 0xBF, 0x5E, 0xDF, 0x7D, 0x90, 0x5C, 0xF1, 0xB5, 0x40, 0xE1, 0x7B, 0xAB, 0x93, 0x7B, 0x4B, 0xD3, 0x62, 0x0D, 0x59, 0x4C, 0x0D, 0x9B, 0xDB, 0xC7, 0x15, 0x99, 0xCE, 0x69, 0xE5, 0x70, 0x6F, + 0xA3, 0x33, 0x20, 0xFE, 0xE0, 0x63, 0x96, 0xCB, 0x97, 0x37, 0xDB, 0x17, 0xA6, 0x2C, 0x96, 0x5F, 0x77, 0xE3, 0x5A, 0xF9, 0xF7, 0x85, 0xBB, 0x0E, 0x50, 0xAB, 0xB8, 0x10, 0x6F, 0xE8, 0xB9, 0x04, + 0xD0, 0xCD, 0x1E, 0x15, 0xB9, 0x25, 0x55, 0xF0, 0x5C, 0x24, 0xE7, 0x6E, 0x94, 0xEC, 0x41, 0xEC, 0x90, 0xE9, 0x60, 0x39, 0xB4, 0xA7, 0xCA, 0x9F, 0x8E, 0xD1, 0x3F, 0x1B, 0xE6, 0xFA, 0x85, 0x03, + 0x44, 0xD4, 0x46, 0xB1, 0x68, 0x3B, 0x04, 0xB7, 0x5B, 0xBA, 0x0C, 0x08, 0xF7, 0x40, 0x25, 0x67, 0x8E, 0x75, 0x40, 0x35, 0x32, 0x21, 0x9F, 0x37, 0x48, 0xF3, 0xC7, 0x3A, 0xA2, 0x0E, 0x34, 0xD5, + 0xEB, 0x1B, 0x0C, 0xBB, 0x58, 0xDA, 0x9A, 0x01, 0xF3, 0x7E, 0x74, 0xC0, 0x63, 0xD0, 0x3A, 0xF3, 0xBA, 0x8F, 0xBA, 0x28, 0x59, 0x2E, 0x41, 0x93, 0x27, 0x0A, 0x00, 0xCD, 0x15, 0x86, 0xF8, 0x33, + 0xDF, 0xA8, 0xDB, 0xF4, 0x0C, 0x15, 0xE7, 0x04, 0xD2, 0x53, 0x65, 0x8C, 0xC0, 0x6C, 0x6A, 0x48, 0x88, 0x1B, 0xAE, 0x68, 0xBD, 0x4C, 0xBE, 0x38, 0xE7, 0xC8, 0x94, 0x87, 0x3E, 0x86, 0x3A, 0x2C, + 0x4C, 0xA2, 0x24, 0xB7, 0x6E, 0xD6, 0x2B, 0xDC, 0x06, 0xD9, 0x0D, 0x7A, 0x7E, 0xC6, 0x8B, 0x62, 0x2E, 0xB3, 0x8A, 0x42, 0x63, 0x93, 0xA4, 0x6E, 0xCA, 0x77, 0xF2, 0x88, 0x11, 0x5A, 0x2A, 0xEF, + 0xAC, 0xC1, 0x5F, 0x44, 0xD9, 0x28, 0x08, 0x8C, 0x5B, 0xC1, 0x9E, 0x08, 0x95, 0xF9, 0x61, 0x9A, 0x08, 0x92, 0x65, 0xB7, 0x6E, 0xEE, 0x26, 0x61, 0xD2, 0x0D, 0x1B, 0xFB, 0x84, 0x79, 0xC2, 0x1C, + 0x15, 0x3E, 0x1D, 0xCA, 0xB0, 0xF0, 0x04, 0xF8, 0x0A, 0x07, 0x2D, 0xE3, 0xE4, 0xAB, 0xB6, 0xF6, 0x99, 0xAE, 0xB8, 0x52, 0xF3, 0x5E, 0x3A, 0xFE, 0x0F, 0xA7, 0x99, 0x35, 0x5E, 0x6B, 0x7E, 0xC6, + 0xD6, 0x59, 0x20, 0xDC, 0xA5, 0x24, 0x8B, 0x45, 0x5B, 0x90, 0xE7, 0xD2, 0xE9, 0x85, 0x9B, 0x18, 0x30, 0x18, 0x65, 0x74, 0xA9, 0x5C, 0xB6, 0x2A, 0x0F, 0x07, 0x3C, 0xAB, 0x4A, 0xCF, 0x1A, 0x9D, + 0x52, 0xA0, 0xD1, 0xF1, 0x76, 0xFE, 0x50, 0x48, 0x77, 0x42, 0xC4, 0x7D, 0x7D, 0x9A, 0x82, 0xC7, 0xEB, 0xCF, 0x67, 0xAE, 0xBC, 0x8C, 0x77, 0xDF, 0xD0, 0x0E, 0x7C, 0xDC, 0xBD, 0xB6, 0x9D, 0x82, + 0x12, 0xD5, 0xD4, 0x56, 0x1E, 0x83, 0x1C, 0x1C, 0xEE, 0xC7, 0x57, 0x14, 0x91, 0x1B, 0xFE, 0xDA, 0xBB, 0x71, 0x4E, 0xDB, 0xEC, 0xD8, 0x6D, 0x3B, 0x5B, 0x65, 0xD1, 0x54, 0x28, 0x83, 0x33, 0xEC, + 0x57, 0x32, 0x7E, 0x2A, 0x27, 0xF2, 0xCD, 0xF1, 0x93, 0xA4, 0x6F, 0xF1, 0x1B, 0x6A, 0x19, 0xD3, 0xDC, 0x71, 0x12, 0x95, 0xB5, 0x08, 0xBF, 0x44, 0x3F, 0x02, 0xAC, 0x9E, 0xB0, 0x4F, 0x37, 0xB6, + 0x7A, 0x8E, 0xD5, 0x49, 0x3F, 0x41, 0xE9, 0x24, 0xF8, 0x48, 0x9F, 0xE2, 0x6A, 0xCA, 0xE5, 0xF6, 0xB0, 0x7B, 0x67, 0x68, 0x31, 0xE2, 0x71, 0xBC, 0xDE, 0x12, 0xC8, 0x0F, 0x65, 0xE8, 0xD0, 0x30, + 0x0D, 0x8F, 0xDE, 0xD5, 0xE9, 0xBF, 0x1A, 0x59, 0xC8, 0x8E, 0xD3, 0x89, 0x45, 0x37, 0x14, 0x51, 0xE1, 0x13, 0x54, 0xB3, 0x07, 0x40, 0x47, 0x61, 0x9B, 0x3A, 0x27, 0x66, 0x58, 0x41, 0x7A, 0xA1, + 0x75, 0x02, 0x67, 0x49, 0xA4, 0xE4, 0x61, 0xF0, 0x59, 0xAF, 0x85, 0xE2, 0x07, 0xF4, 0xD0, 0x21, 0xBB, 0x9C, 0x12, 0xFD, 0xF3, 0x02, 0x90, 0x79, 0x59, 0x72, 0x17, 0xAA, 0x39, 0x15, 0x20, 0x78, + 0x0A, 0x7C, 0x90, 0xC2, 0x32, 0x65, 0x91, 0x14, 0x39, 0x31, 0x84, 0x4F, 0x85, 0x6B, 0x08, 0x4A, 0xC1, 0x7A, 0xEB, 0xC5, 0x93, 0xAC, 0xE9, 0x32, 0xF0, 0xAD, 0x36, 0xE2, 0x13, 0x57, 0xCE, 0xFF, + 0xF3, 0x75, 0xCC, 0xC8, 0x43, 0x42, 0xB8, 0x61, 0x94, 0xA2, 0xBC, 0x77, 0x16, 0x5E, 0xDB, 0x9E, 0xFE, 0x35, 0x93, 0x51, 0xAD, 0x8E, 0x4B, 0xDD, 0x4C, 0xA6, 0xEC, 0xFA, 0x05, 0x20, 0xCC, 0x2F, + 0x46, 0xCF, 0x8A, 0xA1, 0x10, 0x9E, 0x62, 0x68, 0x2B, 0x37, 0xC7, 0x01, 0x42, 0x1F, 0xEE, 0x8F, 0xB5, 0x0A, 0x7D, 0x11, 0xB2, 0xF5, 0xA0, 0x50, 0x14, 0xED, 0x63, 0xBF, 0x91, 0x0C, 0xBB, 0x06, + 0xFA, 0x47, 0xF1, 0xD8, 0x49, 0xAF, 0x11, 0x86, 0xF9, 0x77, 0xD8, 0x07, 0x3D, 0x72, 0x78, 0x3C, 0x4E, 0xE3, 0xC1, 0x9F, 0xF9, 0x5F, 0x23, 0xFC, 0xBD, 0x98, 0x87, 0x9A, 0x46, 0x82, 0xA8, 0xCF, + 0xA7, 0x68, 0x7E, 0xA5, 0x20, 0xCE, 0x58, 0x7E, 0x9A, 0x3E, 0x8F, 0x68, 0x4E, 0x00, 0x09, 0x6A, 0xFE, 0x61, 0x7C, 0xEC, 0xFE, 0x0A, 0x6F, 0xDE, 0xB4, 0x5D, 0x49, 0x3E, 0x7E, 0x35, 0xCC, 0x25, + 0xB6, 0x44, 0xF9, 0xBD, 0xF4, 0xED, 0x10, 0x41, 0x76, 0xCB, 0x96, 0x1B, 0x0C, 0x95, 0x7F, 0x8F, 0x3C, 0xB4, 0x29, 0xFA, 0x14, 0x4D, 0x60, 0x6D, 0x2D, 0xFE, 0x27, 0xC0, 0x90, 0xA3, 0xC2, 0x26, + 0x9C, 0x84, 0xB5, 0xF4, 0x95, 0xC1, 0xC6, 0x6D, 0xD0, 0x79, 0x49, 0x27, 0x4D, 0x99, 0x49, 0x9B, 0x63, 0x3B, 0xFE, 0xA8, 0xF0, 0x44, 0x52, 0x1A, 0xB2, 0x56, 0xF6, 0xF6, 0x24, 0x6A, 0x0C, 0x0A, + 0xEA, 0x3A, 0xDE, 0xFD, 0x14, 0xC8, 0xB1, 0xBE, 0x92, 0xA2, 0x34, 0x7C, 0xD1, 0xFB, 0xEE, 0xAD, 0x71, 0x2C, 0xC0, 0xA8, 0xBE, 0x4C, 0xE0, 0xF4, 0x77, 0x9E, 0xAB, 0x56, 0xF7, 0x1D, 0x9A, 0x7B, + 0x3F, 0x4B, 0xA7, 0x25, 0x24, 0x34, 0xB9, 0x84, 0xDF, 0xE9, 0xD7, 0x59, 0x65, 0x45, 0x66, 0x5F, 0x2F, 0x1E, 0x51, 0x61, 0xC9, 0xDC, 0x9E, 0xA5, 0x89, 0xE3, 0x01, 0xC7, 0x50, 0xB7, 0x3E, 0x55, + 0x26, 0xEF, 0xE6, 0x5F, 0xA0, 0x79, 0x2A, 0xF2, 0xF6, 0x4C, 0xEF, 0xDA, 0x89, 0x1F, 0xB0, 0x81, 0x20, 0x37, 0xFD, 0x0A, 0x31, 0xE7, 0x60, 0x22, 0x83, 0xBE, 0x2B, 0x8D, 0xF6, 0xA7, 0xDB, 0x90, + 0xF3, 0x0F, 0x8B, 0x3B, 0x2D, 0x30, 0xC0, 0x9B, 0x90, 0x0F, 0xA4, 0x00, 0xFD, 0x1C, 0x4B, 0x42, 0x56, 0x3D, 0xF1, 0xEB, 0x8E, 0x39, 0xF9, 0x46, 0x85, 0x95, 0x11, 0x2C, 0x92, 0xD4, 0xA8, 0x43, + 0xEE, 0xE8, 0x70, 0x34, 0x3F, 0xC8, 0x9E, 0x57, 0xC6, 0xBA, 0xCC, 0x37, 0x0D, 0x01, 0x4A, 0x5E, 0x2A, 0xFE, 0xEF, 0x1C, 0x25, 0xEB, 0xA0, 0x80, 0xEC, 0x13, 0x4E, 0x85, 0x8C, 0xFD, 0x65, 0x4D, + 0x0E, 0x96, 0x14, 0x02, 0xD9, 0xA8, 0x07, 0xA9, 0x71, 0xCF, 0x59, 0x2F, 0x33, 0xD1, 0x8E, 0xB2, 0x21, 0x0A, 0x59, 0xE0, 0xFE, 0x94, 0x83, 0x18, 0xE6, 0x0E, 0x6D, 0x61, 0x8D, 0x2D, 0x04, 0x0C, + 0x77, 0x3C, 0xE3, 0x0F, 0x91, 0x64, 0xCC, 0xD4, 0x19, 0xF3, 0x25, 0xF2, 0xFA, 0x3D, 0xDE, 0x63, 0xF5, 0xDF, 0x54, 0x76, 0x42, 0x41, 0x25, 0xE4, 0xA9, 0x23, 0x7F, 0x18, 0xEC, 0x9B, 0x41, 0x09, + 0x9E, 0x89, 0x05, 0xC1, 0x73, 0xDC, 0x60, 0xDD, 0xB3, 0x6D, 0x18, 0x09, 0xC0, 0xF2, 0x2B, 0x3F, 0xA8, 0xB3, 0x9D, 0x84, 0x2E, 0x44, 0xFD, 0xEC, 0x4D, 0xAB, 0x65, 0x0E, 0x9E, 0x60, 0xE3, 0x1C, + 0x05, 0x8E, 0x8C, 0x86, 0x2F, 0x06, 0x9E, 0xD7, 0x00, 0x13, 0x15, 0x77, 0x3A, 0x51, 0x90, 0xC8, 0x64, 0xDC, 0x01, 0xAE, 0x44, 0x5C, 0x59, 0x03, 0xB1, 0x40, 0x07, 0x1A, 0xD7, 0x16, 0xD9, 0x34, + 0x3D, 0x78, 0x8A, 0x0D, 0x36, 0x4A, 0x8F, 0x64, 0x46, 0x5E, 0x68, 0x74, 0x86, 0x12, 0xE9, 0x41, 0xC2, 0xE1, 0xC8, 0xC2, 0x77, 0xCE, 0xF0, 0xF6, 0xCC, 0x08, 0xED, 0xFA, 0xA3, 0xCC, 0x4C, 0x0F, + 0x26, 0x21, 0x59, 0x9C, 0x3A, 0xF4, 0x06, 0xBC, 0x4C, 0xEA, 0x92, 0x33, 0x1B, 0xC6, 0x85, 0x32, 0x12, 0xB2, 0xB3, 0xB1, 0x52, 0x60, 0xFC, 0x54, 0x71, 0x95, 0xBE, 0xCB, 0x95, 0xB0, 0xA5, 0x47, + 0x8E, 0x0F, 0xE5, 0x50, 0xAC, 0xE0, 0xBC, 0x24, 0xE7, 0x2A, 0xC9, 0x83, 0x0F, 0xC7, 0xB4, 0x94, 0xFF, 0x40, 0x9B, 0x49, 0xF9, 0xB3, 0xCC, 0x00, 0x0B, 0x1B, 0x22, 0xE9, 0xFD, 0xDA, 0xBE, 0x17, + 0x68, 0xB8, 0xB1, 0x72, 0x53, 0xE1, 0xC1, 0x6D, 0x44, 0x3F, 0x51, 0xC5, 0xE3, 0x6B, 0xA2, 0x1D, 0xC0, 0x99, 0x62, 0xF8, 0x3F, 0xAF, 0xE8, 0x33, 0x9E, 0xD0, 0xAD, 0x32, 0x37, 0x88, 0xDB, 0xFA, + 0xCE, 0x7B, 0xBA, 0xD5, 0xE8, 0xEA, 0x20, 0x7D, 0x9C, 0x49, 0x5E, 0x57, 0x9A, 0xD7, 0xA7, 0xCB, 0xD3, 0x29, 0xA2, 0x5E, 0xCD, 0x11, 0xE0, 0x98, 0x21, 0x1D, 0x60, 0xEF, 0xB9, 0x01, 0x37, 0x3B, + 0x87, 0xDA, 0xBD, 0x64, 0xA0, 0xAF, 0xE0, 0xDC, 0x2C, 0xA6, 0x15, 0x98, 0xB7, 0xAD, 0x36, 0x70, 0x8B, 0x53, 0x80, 0x0B, 0xE4, 0x57, 0x47, 0x69, 0x82, 0xA3, 0xB9, 0x31, 0x57, 0x14, 0x90, 0x0C, + 0x93, 0x3A, 0x34, 0xB2, 0xAD, 0x9C, 0xBF, 0x16, 0x92, 0xBB, 0xDF, 0x3A, 0x6D, 0xC8, 0x72, 0x03, 0x42, 0x22, 0x89, 0xCD, 0xFD, 0xBC, 0x7D, 0xB7, 0x60, 0x93, 0x69, 0xF0, 0xF2, 0x6B, 0xEB, 0x7F, + 0x12, 0x8E, 0x64, 0x37, 0x13, 0x5C, 0x53, 0x58, 0x26, 0xFF, 0xCC, 0xFA, 0x65, 0xF4, 0xC9, 0xC2, 0x0D, 0xB3, 0xFC, 0xA3, 0x0B, 0xC5, 0xD3, 0xEA, 0x17, 0xA6, 0x93, 0xE5, 0x13, 0x54, 0x3F, 0x9C, + 0xEC, 0x71, 0x51, 0x2B, 0xB8, 0x75, 0x54, 0x9E, 0x3B, 0x5C, 0xB9, 0xF2, 0xF7, 0x7D, 0x2A, 0x80, 0xBF, 0xAC, 0xFC, 0xC4, 0x53, 0x50, 0x8D, 0xDB, 0x91, 0xAE, 0xF1, 0xEA, 0x69, 0xAD, 0x8A, 0x00, + 0x43, 0x99, 0xF5, 0xF6, 0x69, 0x4E, 0x6F, 0x8A, 0x96, 0xE7, 0x3D, 0x4B, 0xE5, 0x02, 0x70, 0x61, 0x73, 0x4F, 0x13, 0x2C, 0x9E, 0xD5, 0x27, 0xF3, 0xB3, 0xC3, 0xC5, 0xC8, 0x48, 0x94, 0x1C, 0x79, + 0xC7, 0x58, 0xCA, 0x48, 0x5E, 0xAD, 0x8F, 0x99, 0x4F, 0x9C, 0x31, 0x31, 0xA2, 0x7B, 0x1E, 0x1E, 0x93, 0xB6, 0xE0, 0x1C, 0xAA, 0x85, 0x04, 0xA0, 0x48, 0xEB, 0xC3, 0xE2, 0x7C, 0x3C, 0xF1, 0xFF, + 0x94, 0xA0, 0x58, 0x60, 0x76, 0x2D, 0x07, 0xE7, 0x90, 0x5E, 0x13, 0x17, 0x53, 0xF5, 0xBA, 0x4D, 0xA6, 0xE7, 0x94, 0xE4, 0x25, 0xEF, 0x41, 0x94, 0xA7, 0x60, 0xBA, 0xBA, 0xA5, 0xBE, 0xED, 0x8D, + 0x39, 0x9C, 0xB3, 0x80, 0x1C, 0x87, 0x27, 0xBC, 0x84, 0x7D, 0x2A, 0x77, 0x1E, 0x02, 0x6F, 0xF6, 0x13, 0x25, 0x5D, 0xD1, 0xA1, 0xF8, 0x8A, 0x1A, 0xA2, 0xC4, 0xA4, 0xBA, 0x48, 0xAE, 0x71, 0xEE, + 0xC2, 0x2B, 0x38, 0xE6, 0x84, 0x2F, 0xD3, 0x18, 0x41, 0x60, 0x06, 0xE8, 0xBA, 0x1A, 0x96, 0x73, 0xD1, 0x43, 0xEB, 0x80, 0x49, 0x1F, 0x98, 0xD6, 0x34, 0xB4, 0x6C, 0xAB, 0x31, 0x0E, 0xCC, 0x1F, + 0x70, 0x22, 0x97, 0xF6, 0xF0, 0xA8, 0x4A, 0x2B, 0xC2, 0xB7, 0x90, 0xAF, 0xEA, 0xAF, 0xE7, 0x3F, 0x06, 0x3B, 0x3A, 0xA4, 0xFF, 0xAE, 0xD3, 0x52, 0x67, 0xFD, 0x2B, 0x52, 0x69, 0x50, 0x3C, 0x88, + 0x83, 0xAD, 0x7D, 0x9E, 0x77, 0xD4, 0x67, 0xB3, 0xB3, 0x5B, 0xDC, 0xD5, 0xDD, 0xFC, 0x58, 0x02, 0x41, 0x78, 0x24, 0x6D, 0xF1, 0x24, 0x66, 0x23, 0x8F, 0x28, 0x6D, 0x85, 0xD9, 0x2A, 0x23, 0x55, + 0xC6, 0x3A, 0xF9, 0xA4, 0x59, 0x07, 0x7E, 0xAF, 0x28, 0xCD, 0xAD, 0x26, 0xCC, 0x71, 0xC6, 0xFF, 0x60, 0x7B, 0x50, 0xBC, 0xAB, 0x69, 0x3E, 0x09, 0x1F, 0x25, 0x09, 0x39, 0xC5, 0x23, 0x5C, 0x61, + 0x6B, 0x84, 0x01, 0x2C, 0x12, 0xFA, 0xAB, 0xE4, 0x0A, 0x66, 0x16, 0x84, 0x24, 0x01, 0x99, 0xB2, 0xDD, 0x9C, 0x86, 0x17, 0x9A, 0xBF, 0x8D, 0x3B, 0x96, 0xDE, 0xD1, 0x67, 0x50, 0x24, 0x6A, 0x8F, + 0x03, 0x30, 0x5E, 0xE0, 0x67, 0xAD, 0xF2, 0x2C, 0x39, 0xEC, 0xB1, 0xFA, 0xF8, 0x57, 0x8D, 0xED, 0x3A, 0x25, 0xE5, 0x44, 0x85, 0xA1, 0x0B, 0xC9, 0x8A, 0x82, 0x4D, 0xBD, 0xFC, 0x2F, 0x6B, 0x14, + 0x5F, 0x42, 0x16, 0xA2, 0x9D, 0xB5, 0xFA, 0x7A, 0x9C, 0x2B, 0x6D, 0x51, 0xCB, 0x37, 0x59, 0xC3, 0xC5, 0x89, 0x46, 0xDD, 0x2E, 0x64, 0x8A, 0x1F, 0x36, 0xD2, 0x0C, 0x09, 0xBC, 0x58, 0xBA, 0x91, + 0xE2, 0x57, 0x03, 0x63, 0x98, 0xB7, 0xD5, 0xDA, 0x10, 0x6E, 0x5C, 0x6B, 0xDE, 0x1F, 0xF1, 0x98, 0xB9, 0x5D, 0x12, 0xDE, 0xFD, 0xC5, 0x4A, 0x5B, 0x3D, 0xD5, 0x5A, 0xFF, 0x42, 0x00, 0xAA, 0x27, + 0xED, 0x5B, 0xCB, 0xD7, 0xFD, 0x6D, 0x6A, 0xD9, 0x1E, 0x15, 0x96, 0x53, 0x35, 0x2E, 0xDE, 0xE8, 0xF9, 0x60, 0xE4, 0xEB, 0x6F, 0x09, 0x42, 0xAF, 0x52, 0x51, 0xEF, 0x39, 0xC1, 0xAB, 0xBD, 0xC4, + 0x2D, 0x8B, 0xE0, 0xB8, 0x80, 0x06, 0x7A, 0x79, 0xCE, 0xB1, 0x69, 0x90, 0x1E, 0xA8, 0x14, 0x71, 0xC4, 0xDC, 0x78, 0x23, 0x32, 0xBA, 0xC6, 0x26, 0x40, 0xA2, 0x80, 0xDD, 0x9B, 0x32, 0x3C, 0xC5, + 0xC3, 0x93, 0xB2, 0xB3, 0x7F, 0xE8, 0x21, 0xBA, 0x45, 0xD5, 0xC0, 0x5B, 0xCF, 0xEB, 0x11, 0x75, 0xF7, 0xE5, 0xAE, 0x12, 0xE7, 0x7D, 0xCF, 0x92, 0xB5, 0xDC, 0xB7, 0xF4, 0x87, 0x52, 0xA7, 0x2E, + 0x6F, 0x6E, 0x25, 0x0A, 0x65, 0x27, 0xF5, 0xA6, 0xF3, 0x59, 0xEB, 0x4D, 0x1C, 0x69, 0xDD, 0x65, 0x1D, 0x89, 0xF3, 0xF2, 0x22, 0x9C, 0xEF, 0x12, 0xF5, 0x01, 0x2A, 0x96, 0x68, 0xD2, 0x60, 0xF7, + 0x79, 0x3C, 0x91, 0xA7, 0x62, 0x2E, 0x5E, 0xCC, 0x3B, 0x58, 0x21, 0xBA, 0x43, 0x9E, 0xCC, 0x75, 0x33, 0xDF, 0xB5, 0x32, 0xA2, 0xB6, 0x4A, 0x96, 0x0C, 0x4C, 0xA0, 0x43, 0x1B, 0x3D, 0x09, 0x57, + 0x3B, 0x0B, 0x63, 0x75, 0x74, 0x8A, 0x47, 0x5D, 0xD0, 0xDC, 0x92, 0x90, 0xCE, 0xCA, 0xFD, 0x05, 0x9D, 0xC0, 0x03, 0x8C, 0xD1, 0x29, 0x54, 0x68, 0xA4, 0xCE, 0x11, 0x8E, 0x8B, 0x5B, 0x03, 0x70, + 0x7C, 0x56, 0xB1, 0x4E, 0xDF, 0x9A, 0xF6, 0x21, 0x9E, 0xF7, 0x68, 0xDF, 0xCF, 0x3D, 0x45, 0x52, 0x84, 0x4C, 0x58, 0x54, 0x1C, 0xFA, 0x0D, 0x17, 0x5C, 0xF7, 0xEF, 0xBB, 0x5F, 0xA2, 0x81, 0x30, + 0xCB, 0x78, 0xD8, 0x21, 0x20, 0xAC, 0xB7, 0xB4, 0x03, 0xCC, 0x75, 0xB8, 0x1C, 0x3F, 0xF1, 0x24, 0x0D, 0xBE, 0xF6, 0xE7, 0xF1, 0xCB, 0xA8, 0x80, 0x7A, 0x5A, 0x21, 0x31, 0x0C, 0x29, 0x79, 0x5B, + 0x4E, 0x32, 0xCC, 0x4A, 0x49, 0xC4, 0x7F, 0xB5, 0x1B, 0xAC, 0xDD, 0x14, 0x3C, 0xD4, 0x95, 0xC0, 0xF5, 0xC1, 0x0D, 0xF9, 0xFE, 0x06, 0xBF, 0x22, 0x41, 0xBC, 0xEC, 0xEA, 0x21, 0x29, 0xD3, 0xDB, + 0xC5, 0x7B, 0xA1, 0x06, 0x8F, 0x43, 0x2D, 0xDF, 0x57, 0x24, 0x14, 0xAD, 0x6F, 0x12, 0xD6, 0x37, 0x10, 0x64, 0xFD, 0xEE, 0x0D, 0x5C, 0xCF, 0x97, 0x30, 0xBA, 0xD1, 0xBB, 0xB4, 0x74, 0x9C, 0x87, + 0x00, 0x7E, 0xB0, 0xBD, 0x66, 0x60, 0xC9, 0x94, 0xFF, 0xCC, 0x7F, 0xC7, 0xD7, 0x69, 0xAB, 0xF0, 0x16, 0x0B, 0xA6, 0xDF, 0x93, 0xB7, 0x19, 0xC7, 0x3B, 0x6D, 0xA6, 0xB5, 0xB1, 0x51, 0xDC, 0x44, + 0xA3, 0x9D, 0x54, 0x3A, 0xF0, 0x73, 0xD3, 0x74, 0xE0, 0x4B, 0x03, 0x3D, 0x1A, 0xFA, 0xB9, 0x59, 0x08, 0x2E, 0x5E, 0x02, 0xB2, 0x07, 0xA2, 0x55, 0x10, 0x5B, 0xB4, 0xD4, 0xC7, 0xE6, 0xB2, 0x5A, + 0x62, 0x65, 0x8C, 0x13, 0xCF, 0x91, 0x35, 0x1F, 0x50, 0xCC, 0x23, 0x74, 0x16, 0x41, 0x06, 0x67, 0xFA, 0xA8, 0x9D, 0xEC, 0x53, 0x8E, 0xB1, 0xAE, 0x2C, 0xBE, 0x55, 0x8D, 0xCC, 0xEE, 0xB5, 0xAA, + 0xE9, 0x08, 0xBD, 0x1E, 0xE7, 0x90, 0xA8, 0x43, 0xDB, 0x06, 0x73, 0x29, 0xC7, 0x05, 0x04, 0x5B, 0xBC, 0x0A, 0x7A, 0xCB, 0xA0, 0xA5, 0x1D, 0xB8, 0x39, 0xAA, 0xAF, 0xB6, 0xA3, 0x6F, 0x4E, 0xC1, + 0xC2, 0xD4, 0x3F, 0x5B, 0xF1, 0xAC, 0x55, 0xAA, 0x6E, 0x82, 0x0B, 0x26, 0xC4, 0x7C, 0x38, 0x06, 0x0C, 0x61, 0xB1, 0xE3, 0xA7, 0xB2, 0xCC, 0x26, 0x1D, 0x54, 0xC0, 0xB3, 0x4F, 0x5A, 0x25, 0x74, + 0xF5, 0x24, 0x3B, 0x2A, 0x08, 0x29, 0xBE, 0xBB, 0xA9, 0x93, 0x30, 0x11, 0x89, 0x7E, 0x98, 0x08, 0x69, 0xD6, 0xDD, 0x5A, 0xC7, 0xB3, 0x1A, 0x9B, 0xA9, 0xAA, 0x98, 0xA3, 0xEC, 0x20, 0x14, 0x5A, + 0x81, 0xB2, 0x7B, 0x33, 0xAB, 0x66, 0x62, 0xDB, 0x34, 0x87, 0xFC, 0xAA, 0x32, 0xBA, 0xFA, 0x6E, 0x1B, 0x28, 0x55, 0x02, 0x5D, 0x5F, 0xB5, 0xC8, 0x69, 0x67, 0x75, 0x20, 0x03, 0xBE, 0x2F, 0xD8, + 0xE2, 0x98, 0xB3, 0x73, 0xD1, 0x01, 0x7E, 0xD7, 0xD1, 0xAC, 0xCB, 0x6D, 0x31, 0x6F, 0x19, 0x40, 0x19, 0x76, 0xF2, 0x13, 0x38, 0x62, 0xAA, 0x3C, 0xC4, 0x82, 0x39, 0x0C, 0xE5, 0x5D, 0x1E, 0x63, + 0xEC, 0x4A, 0x40, 0xFE, 0x82, 0x6E, 0x62, 0x8D, 0x3E, 0x81, 0x1C, 0xDF, 0x57, 0x27, 0x70, 0x48, 0x0F, 0x20, 0x3A, 0x36, 0xA6, 0xFD, 0xAB, 0xD1, 0xD2, 0xCB, 0x6D, 0xE5, 0xD7, 0xC2, 0xA3, 0x2A, + 0xD4, 0x5B, 0xF3, 0x72, 0x5F, 0x59, 0x9D, 0x29, 0xD0, 0xF1, 0x34, 0x2E, 0x3B, 0x57, 0x98, 0x63, 0x3B, 0x6E, 0x72, 0xA4, 0x3F, 0x48, 0x33, 0xF2, 0x21, 0xEA, 0x9D, 0x90, 0x4B, 0x00, 0x2D, 0x8D, + 0x13, 0xF6, 0xE7, 0x44, 0x10, 0x05, 0xBD, 0x3D, 0xA8, 0x8B, 0x64, 0x9B, 0xEE, 0x65, 0xAC, 0x9F, 0xF6, 0xDB, 0x40, 0x7E, 0xED, 0x65, 0x3E, 0x18, 0x87, 0x35, 0xF5, 0xFF, 0xDB, 0xBC, 0x4A, 0x1E, + 0x2E, 0x08, 0x9C, 0x7B, 0xC4, 0x60, 0x6B, 0xCA, 0x32, 0x34, 0xF2, 0xD8, 0x9D, 0x40, 0x39, 0x55, 0xF4, 0x4A, 0x44, 0x4A, 0x42, 0xA2, 0x0D, 0xFE, 0xE5, 0xC4, 0x9C, 0x84, 0x42, 0x5E, 0x1A, 0x17, + 0x2C, 0xA4, 0x44, 0x82, 0xFE, 0xBB, 0x45, 0x16, 0xDD, 0x4B, 0x64, 0x9C, 0x6F, 0x31, 0x5A, 0x7E, 0x2D, 0xDB, 0xE1, 0x94, 0xFE, 0xA2, 0xA9, 0x17, 0x28, 0xE1, 0xDF, 0x45, 0x11, 0x08, 0xE2, 0x10, + 0x56, 0xA7, 0xBD, 0x3D, 0x45, 0x5B, 0x8A, 0xA8, 0xB7, 0x11, 0x1C, 0x26, 0x79, 0x7C, 0xB7, 0xBA, 0x0C, 0x24, 0x60, 0x8E, 0x93, 0xDC, 0xFC, 0x31, 0x41, 0x5D, 0x98, 0xCB, 0xD1, 0xFE, 0x1A, 0x20, + 0x7C, 0x81, 0xCD, 0xEB, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x09, 0x10, 0x17, 0x1E, 0x24, + }, + }, + { + .name = "Dilithium Round 3, Level 5 (8-7) KAT 0 (PKCS#8/SPKI)", + .version = 0, + .keyform = 0, + .rho_len = 0, + .seed_len = 0, + .tr_len = 0, + .s1_len = 0, + .s2_len = 0, + .t0_len = 0, + .t1_len = 0, + .pkcs8_len = 7492, + .pkcs8 = { + 0x30, 0x82, 0x1D, 0x40, 0x02, 0x01, 0x00, 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0B, 0x07, 0x08, 0x07, 0x05, 0x00, 0x04, 0x82, 0x1D, 0x28, 0x30, 0x82, 0x1D, 0x24, + 0x02, 0x01, 0x00, 0x03, 0x21, 0x00, 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, + 0x38, 0xD5, 0x06, 0xD8, 0x5B, 0xEF, 0x03, 0x21, 0x00, 0x39, 0x4D, 0x16, 0x95, 0x05, 0x9D, 0xFF, 0x40, 0xAE, 0x25, 0x6C, 0x5D, 0x5E, 0xDA, 0xBF, 0xB6, 0x9F, 0x5F, 0x40, 0xF3, 0x7A, 0x58, 0x8F, + 0x50, 0x53, 0x2C, 0xA4, 0x08, 0xA8, 0x16, 0x8A, 0xB1, 0x03, 0x21, 0x00, 0x85, 0xF6, 0x84, 0xAE, 0xB4, 0x01, 0xB9, 0xAA, 0xAF, 0x81, 0x2A, 0x00, 0xE1, 0x24, 0xFF, 0x56, 0xFE, 0xE5, 0x1B, 0xA7, + 0xC1, 0x12, 0x82, 0x61, 0x7F, 0x05, 0x72, 0xCC, 0x79, 0x1D, 0xC8, 0x1C, 0x03, 0x82, 0x02, 0xA1, 0x00, 0xC0, 0xA6, 0x71, 0x1A, 0x96, 0x6C, 0x11, 0x31, 0x2A, 0xD9, 0xA8, 0x21, 0xD8, 0x08, 0x65, + 0x42, 0xA6, 0x00, 0xA4, 0xB4, 0x2C, 0x19, 0x40, 0x72, 0x02, 0x42, 0x62, 0x81, 0x06, 0x21, 0x0A, 0x43, 0x85, 0x23, 0x31, 0x70, 0x93, 0x08, 0x10, 0x8B, 0x18, 0x8C, 0x02, 0x24, 0x92, 0xC1, 0xB2, + 0x84, 0x12, 0xC4, 0x21, 0x8B, 0x04, 0x21, 0x81, 0xC8, 0x61, 0x02, 0x48, 0x05, 0x9C, 0x92, 0x01, 0xC0, 0x34, 0x88, 0x19, 0x32, 0x6C, 0x58, 0x20, 0x46, 0x89, 0x18, 0x68, 0xA2, 0xC2, 0x8D, 0x82, + 0x34, 0x6A, 0x1C, 0x09, 0x42, 0x00, 0xA2, 0x8C, 0xE3, 0xA6, 0x49, 0x1C, 0x11, 0x2C, 0xC2, 0x48, 0x12, 0xE0, 0x90, 0x21, 0x91, 0x98, 0x50, 0x62, 0xC0, 0x84, 0x62, 0x24, 0x51, 0xCA, 0x06, 0x2C, + 0x64, 0x24, 0x0E, 0x1B, 0xB3, 0x31, 0x24, 0x96, 0x85, 0x4B, 0x46, 0x06, 0xDB, 0x26, 0x68, 0xC3, 0x82, 0x68, 0x44, 0x10, 0x46, 0xC9, 0xB6, 0x21, 0x14, 0x04, 0x81, 0x14, 0x45, 0x50, 0x24, 0x42, + 0x08, 0x44, 0x22, 0x71, 0x0B, 0x92, 0x45, 0x9A, 0xA0, 0x81, 0x1A, 0x91, 0x70, 0x9C, 0x24, 0x10, 0x03, 0x95, 0x70, 0x04, 0xC5, 0x04, 0xC8, 0x26, 0x92, 0xD2, 0x92, 0x00, 0xC0, 0xB2, 0x60, 0xC0, + 0xA2, 0x68, 0x09, 0x19, 0x0A, 0xA2, 0x30, 0x0E, 0x18, 0x89, 0x69, 0xE0, 0x00, 0x8D, 0xD8, 0x48, 0x62, 0xDA, 0x14, 0x71, 0x20, 0x18, 0x05, 0x19, 0x07, 0x44, 0x04, 0x12, 0x40, 0x9B, 0x12, 0x40, + 0x11, 0x80, 0x10, 0xD1, 0x42, 0x81, 0x99, 0x28, 0x50, 0x8B, 0x10, 0x91, 0x02, 0x24, 0x64, 0xA0, 0x20, 0x6D, 0x12, 0x46, 0x21, 0x1C, 0x83, 0x8C, 0x1B, 0x47, 0x69, 0x01, 0x06, 0x90, 0xCC, 0x06, + 0x24, 0x81, 0x84, 0x69, 0x20, 0x98, 0x2C, 0x24, 0x12, 0x05, 0x21, 0xB1, 0x50, 0x41, 0x36, 0x02, 0x98, 0x44, 0x6E, 0xD1, 0xA6, 0x31, 0x11, 0x05, 0x6A, 0xD3, 0xA8, 0x40, 0xCA, 0xA8, 0x4C, 0x62, + 0xB0, 0x00, 0x03, 0x13, 0x4A, 0x53, 0x34, 0x46, 0x14, 0x19, 0x40, 0x04, 0xC5, 0x4C, 0xE3, 0x06, 0x69, 0x5A, 0xB0, 0x89, 0x61, 0x16, 0x8E, 0xCB, 0x10, 0x80, 0x8B, 0x16, 0x8E, 0xD9, 0x90, 0x64, + 0x0B, 0x94, 0x60, 0x24, 0x83, 0x85, 0x1A, 0xB3, 0x04, 0x54, 0x26, 0x22, 0x51, 0xB8, 0x25, 0x1C, 0x42, 0x4A, 0x0B, 0x81, 0x48, 0x42, 0xC4, 0x44, 0x5A, 0x10, 0x20, 0x23, 0x80, 0x84, 0x09, 0xB7, + 0x25, 0x4C, 0xC6, 0x48, 0x14, 0x85, 0x4D, 0x19, 0x38, 0x0E, 0x60, 0x16, 0x51, 0xD8, 0x32, 0x6A, 0x0A, 0x91, 0x89, 0x08, 0xC1, 0x70, 0xE0, 0x96, 0x4D, 0x18, 0x46, 0x8C, 0x01, 0x32, 0x8D, 0x91, + 0xC4, 0x05, 0x4A, 0x00, 0x61, 0x23, 0x08, 0x68, 0xA2, 0x10, 0x42, 0x10, 0xA8, 0x61, 0x13, 0x06, 0x21, 0x8A, 0x24, 0x8E, 0x62, 0x06, 0x89, 0xC9, 0xB2, 0x45, 0x08, 0x27, 0x84, 0x51, 0x20, 0x0D, + 0x98, 0x04, 0x66, 0xDC, 0x42, 0x05, 0x44, 0x24, 0x85, 0x24, 0x26, 0x28, 0x22, 0x21, 0x61, 0x20, 0x16, 0x09, 0x0B, 0xA6, 0x2C, 0x0A, 0x11, 0x44, 0xE0, 0x92, 0x81, 0x58, 0x48, 0x0D, 0x42, 0x22, + 0x10, 0xA0, 0x06, 0x09, 0x8B, 0x24, 0x6E, 0x81, 0x28, 0x8C, 0xC0, 0x24, 0x80, 0x90, 0x30, 0x8D, 0x84, 0x36, 0x40, 0x4C, 0xA6, 0x84, 0x50, 0x04, 0x24, 0x94, 0xB6, 0x8D, 0xA2, 0x92, 0x6D, 0x18, + 0xB3, 0x44, 0xA0, 0x00, 0x85, 0xE3, 0xB8, 0x05, 0x14, 0x05, 0x04, 0xA4, 0xC2, 0x90, 0x84, 0x22, 0x81, 0xC3, 0x26, 0x2D, 0x0B, 0x20, 0x66, 0xCC, 0x90, 0x31, 0x98, 0x38, 0x28, 0x10, 0x16, 0x6C, + 0xC1, 0x34, 0x45, 0xC0, 0x10, 0x22, 0x24, 0xC6, 0x88, 0x03, 0x46, 0x32, 0xD8, 0x40, 0x90, 0x1C, 0x20, 0x68, 0x04, 0x15, 0x28, 0x9A, 0x18, 0x81, 0x44, 0x98, 0x8D, 0x9C, 0x20, 0x6E, 0x9C, 0x30, + 0x2C, 0xC1, 0xB8, 0x20, 0x61, 0x42, 0x21, 0x08, 0x03, 0x10, 0xA0, 0xC2, 0x8C, 0x58, 0x12, 0x85, 0x53, 0x20, 0x4C, 0x03, 0x30, 0x81, 0x4C, 0xA4, 0x8D, 0x44, 0xC0, 0x8D, 0x51, 0x40, 0x4C, 0x1C, + 0xA7, 0x2C, 0x44, 0x08, 0x65, 0xA0, 0x38, 0x40, 0xDA, 0x20, 0x80, 0x81, 0x06, 0x85, 0x8C, 0x26, 0x0D, 0xE2, 0xA8, 0x8C, 0x9C, 0x44, 0x11, 0x59, 0x42, 0x28, 0xC4, 0x26, 0x04, 0x44, 0x14, 0x26, + 0xA1, 0x42, 0x64, 0x08, 0xC0, 0x85, 0x11, 0x01, 0x86, 0x9B, 0x48, 0x31, 0x99, 0xB2, 0x0C, 0x80, 0x46, 0x44, 0x59, 0xA8, 0x8C, 0x00, 0x42, 0x08, 0x98, 0x82, 0x90, 0x0A, 0xB5, 0x45, 0x62, 0x24, + 0x48, 0x12, 0x96, 0x05, 0x44, 0x12, 0x46, 0x00, 0xC8, 0x88, 0x13, 0xA0, 0x61, 0xE1, 0x28, 0x4D, 0x0A, 0xB9, 0x91, 0x4B, 0x96, 0x20, 0x99, 0xB8, 0x44, 0x00, 0x31, 0x4E, 0x98, 0x12, 0x85, 0x00, + 0xB6, 0x01, 0x83, 0xA0, 0x0D, 0x14, 0x15, 0x0E, 0x18, 0x81, 0x10, 0x19, 0x01, 0x22, 0x4A, 0x06, 0x68, 0x03, 0x82, 0x03, 0x01, 0x00, 0x1A, 0x49, 0x8D, 0xE1, 0xA2, 0x84, 0x11, 0xC6, 0x31, 0x21, + 0x26, 0x25, 0x91, 0xA0, 0x6D, 0x03, 0x05, 0x24, 0xA1, 0xB6, 0x08, 0x94, 0x44, 0x72, 0x43, 0x34, 0x12, 0x5B, 0xB4, 0x20, 0x41, 0xB6, 0x50, 0xD0, 0x88, 0x8D, 0x0B, 0x07, 0x4D, 0x1C, 0x94, 0x64, + 0x4C, 0x20, 0x8E, 0x8B, 0x88, 0x08, 0xE0, 0x30, 0x09, 0x44, 0x20, 0x05, 0x49, 0x86, 0x4D, 0x03, 0x13, 0x4E, 0x19, 0xC9, 0x84, 0x09, 0x37, 0x61, 0x1A, 0x43, 0x68, 0x4A, 0x80, 0x90, 0x02, 0x04, + 0x31, 0x1C, 0x17, 0x42, 0x18, 0x40, 0x80, 0xC8, 0x30, 0x8E, 0xE1, 0xA2, 0x41, 0xC3, 0x34, 0x04, 0xA3, 0x28, 0x22, 0x51, 0x24, 0x71, 0x82, 0x84, 0x01, 0x1B, 0xC0, 0x64, 0x23, 0x47, 0x72, 0x82, + 0x14, 0x66, 0x5B, 0x38, 0x68, 0xE1, 0xC6, 0x29, 0x9B, 0x90, 0x40, 0x60, 0x38, 0x86, 0x83, 0xA0, 0x40, 0x84, 0x20, 0x04, 0x4C, 0x94, 0x01, 0x10, 0x25, 0x8D, 0x82, 0x02, 0x4D, 0x9A, 0xB2, 0x69, + 0x20, 0x15, 0x10, 0x60, 0x46, 0x2D, 0xC2, 0x14, 0x2E, 0x0C, 0xA8, 0x2C, 0x54, 0x16, 0x22, 0x03, 0x46, 0x89, 0x92, 0x06, 0x60, 0x08, 0x07, 0x82, 0x0B, 0x47, 0x44, 0x48, 0x98, 0x09, 0x09, 0x43, + 0x0E, 0xE4, 0x32, 0x0A, 0x1A, 0xC0, 0x65, 0xC0, 0xA4, 0x21, 0x44, 0xB2, 0x91, 0x58, 0xC6, 0x04, 0x11, 0x45, 0x20, 0xC4, 0xA4, 0x21, 0x02, 0xA0, 0x70, 0x21, 0x22, 0x26, 0x23, 0xB2, 0x68, 0x4B, + 0x08, 0x40, 0x01, 0x03, 0x91, 0x8B, 0x34, 0x81, 0x1A, 0x04, 0x04, 0x0C, 0xB0, 0x05, 0xC2, 0x92, 0x69, 0x90, 0x14, 0x68, 0x04, 0x46, 0x49, 0x14, 0x83, 0x49, 0xA2, 0x34, 0x89, 0x19, 0xC7, 0x28, + 0x94, 0x44, 0x71, 0x00, 0xC9, 0x49, 0x58, 0x38, 0x72, 0x02, 0x02, 0x90, 0x42, 0xC6, 0x4C, 0x0C, 0x17, 0x32, 0x48, 0xC6, 0x8C, 0x59, 0x28, 0x31, 0x09, 0xB7, 0x28, 0xCB, 0x48, 0x0E, 0x9A, 0x22, + 0x85, 0x1C, 0xB9, 0x11, 0xE3, 0xC6, 0x30, 0xC3, 0x48, 0x28, 0xCC, 0xB8, 0x28, 0x03, 0xC8, 0x08, 0xA4, 0xB6, 0x04, 0xD0, 0x18, 0x8C, 0x60, 0x18, 0x72, 0xD0, 0x20, 0x92, 0x82, 0x02, 0x2E, 0x59, + 0x18, 0x89, 0x08, 0x19, 0x32, 0xC9, 0x06, 0x52, 0x60, 0x90, 0x8C, 0x09, 0x80, 0x29, 0xA4, 0xB4, 0x8C, 0x8C, 0x34, 0x82, 0x08, 0x42, 0x10, 0x02, 0x00, 0x08, 0x13, 0x01, 0x50, 0x83, 0xB6, 0x08, + 0x41, 0x94, 0x4D, 0x1B, 0x49, 0x6C, 0x19, 0x39, 0x11, 0xCB, 0x32, 0x41, 0x02, 0xC0, 0x65, 0x48, 0x88, 0x91, 0x9B, 0x98, 0x61, 0x08, 0xB5, 0x04, 0x49, 0xB4, 0x45, 0xD3, 0x30, 0x01, 0x98, 0x04, + 0x6D, 0x53, 0x00, 0x89, 0x42, 0x32, 0x60, 0x8C, 0xB0, 0x90, 0x64, 0x88, 0x68, 0xD4, 0x32, 0x45, 0x48, 0x14, 0x71, 0x14, 0x98, 0x05, 0x81, 0x00, 0x22, 0xDB, 0x44, 0x69, 0xD9, 0x24, 0x89, 0x11, + 0x41, 0x12, 0x09, 0x19, 0x50, 0x92, 0xA0, 0x84, 0xC0, 0x34, 0x22, 0x4A, 0x24, 0x10, 0xDA, 0xC8, 0x09, 0xD2, 0xA8, 0x0D, 0x22, 0x85, 0x21, 0x8B, 0xC8, 0x90, 0xC1, 0x00, 0x66, 0x5C, 0xC0, 0x25, + 0x99, 0xA4, 0x61, 0x1A, 0xA4, 0x11, 0x0A, 0x24, 0x28, 0x5B, 0xC4, 0x48, 0x13, 0x14, 0x89, 0x63, 0x92, 0x61, 0x20, 0x30, 0x0C, 0x40, 0x02, 0x25, 0x21, 0x88, 0x28, 0x24, 0x01, 0x8C, 0x10, 0x81, + 0x6D, 0x4C, 0x42, 0x49, 0x01, 0x22, 0x2D, 0xC1, 0x96, 0x0C, 0x08, 0x48, 0x90, 0x01, 0xC1, 0x30, 0x23, 0xC1, 0x89, 0xA1, 0xC4, 0x64, 0x12, 0x97, 0x09, 0xCC, 0x90, 0x91, 0x60, 0x20, 0x66, 0x1B, + 0x96, 0x48, 0x82, 0xA8, 0x71, 0x91, 0xC0, 0x65, 0xDB, 0xC2, 0x01, 0x84, 0x36, 0x0A, 0x09, 0x24, 0x29, 0x52, 0x10, 0x4E, 0xDB, 0x24, 0x0A, 0x61, 0x02, 0x10, 0x20, 0x38, 0x25, 0x98, 0x34, 0x60, + 0x82, 0x24, 0x30, 0xC4, 0x12, 0x49, 0xC0, 0xA2, 0x05, 0x0C, 0x08, 0x85, 0x93, 0x28, 0x09, 0x63, 0xB2, 0x05, 0x23, 0x96, 0x20, 0x42, 0x12, 0x0D, 0xD1, 0xC0, 0x10, 0x08, 0xC5, 0x40, 0xC1, 0x82, + 0x65, 0x1B, 0x15, 0x92, 0xA4, 0x14, 0x51, 0x84, 0x04, 0x26, 0x53, 0x42, 0x52, 0x24, 0x23, 0x6D, 0x9C, 0x28, 0x4E, 0x50, 0x14, 0x05, 0x8C, 0x20, 0x80, 0x24, 0x26, 0x65, 0x61, 0x44, 0x4C, 0x02, + 0x11, 0x20, 0xC8, 0xC0, 0x4C, 0x18, 0xA0, 0x0D, 0x00, 0x38, 0x70, 0x99, 0x16, 0x12, 0xA1, 0x16, 0x40, 0xC4, 0x18, 0x45, 0x09, 0x93, 0x88, 0x4C, 0x82, 0x21, 0xCB, 0xB2, 0x81, 0x21, 0x26, 0x61, + 0xD1, 0xA8, 0x24, 0x41, 0x30, 0x84, 0x08, 0x80, 0x71, 0x00, 0xC6, 0x20, 0x52, 0x42, 0x92, 0x89, 0x24, 0x12, 0xA4, 0x26, 0x89, 0xE3, 0xB0, 0x88, 0x21, 0x98, 0x8C, 0x11, 0x96, 0x2C, 0xE1, 0x96, + 0x20, 0x51, 0xC2, 0x81, 0x20, 0x91, 0x80, 0x94, 0x16, 0x6E, 0x14, 0x94, 0x60, 0x20, 0xC9, 0x45, 0x9B, 0x22, 0x45, 0xA2, 0x38, 0x20, 0xC0, 0x36, 0x08, 0x60, 0x90, 0x8D, 0x41, 0x06, 0x02, 0x5B, + 0x06, 0x6E, 0xE1, 0x40, 0x0A, 0x89, 0x34, 0x6C, 0x1A, 0xB2, 0x69, 0xA4, 0x16, 0x10, 0x03, 0x33, 0x0E, 0x1A, 0x42, 0x28, 0x03, 0x19, 0x6E, 0x11, 0x44, 0x84, 0x0B, 0x24, 0x4A, 0x1C, 0x16, 0x6A, + 0x19, 0x98, 0x40, 0x03, 0xA2, 0x85, 0x41, 0xC0, 0x8C, 0xD2, 0x22, 0x61, 0x0C, 0x82, 0x10, 0x5A, 0xB0, 0x0D, 0x21, 0x14, 0x72, 0x5A, 0x82, 0x80, 0x02, 0x86, 0x10, 0x0C, 0x27, 0x26, 0x5C, 0x48, + 0x6E, 0xC9, 0x40, 0x6C, 0x1B, 0x49, 0x04, 0xE4, 0xB8, 0x49, 0xDB, 0x32, 0x8A, 0x9C, 0x24, 0x2C, 0x40, 0x38, 0x80, 0x22, 0xA9, 0x45, 0x03, 0x82, 0x0D, 0x01, 0x00, 0x12, 0x29, 0xA4, 0xE6, 0x5E, + 0xD3, 0x1C, 0x79, 0x3E, 0xCB, 0x5B, 0x89, 0xC5, 0x5D, 0xC3, 0x33, 0xA2, 0x77, 0xBF, 0x5C, 0x41, 0x28, 0xA2, 0x14, 0x01, 0xAF, 0xA8, 0xD4, 0x28, 0xC8, 0x21, 0xE9, 0x7A, 0xEA, 0x05, 0xB3, 0xAD, + 0x29, 0x23, 0xBD, 0x97, 0x10, 0x87, 0x1C, 0xE8, 0xB3, 0xB1, 0x1A, 0x71, 0x1C, 0x9A, 0xAC, 0xBA, 0x10, 0x8C, 0xAF, 0x43, 0xA1, 0x72, 0xD6, 0x59, 0x94, 0x01, 0xDB, 0x89, 0x68, 0x1D, 0x0B, 0x87, + 0x4E, 0xC3, 0x57, 0xA5, 0x29, 0x5C, 0x0A, 0x08, 0xD5, 0x89, 0xC4, 0x53, 0x9F, 0x9C, 0x59, 0xF3, 0x3F, 0x06, 0x44, 0x64, 0x41, 0x20, 0x49, 0x84, 0xE1, 0xF9, 0x87, 0x3C, 0x1F, 0x97, 0x75, 0xB9, + 0x7E, 0xD4, 0x00, 0xC9, 0x98, 0xB0, 0x51, 0x62, 0xB6, 0x18, 0x98, 0x61, 0xF2, 0x8D, 0xAE, 0x36, 0xC2, 0x13, 0x37, 0x65, 0x71, 0x11, 0x76, 0xCA, 0xAF, 0x5A, 0x1D, 0xCB, 0x2A, 0x0E, 0x22, 0x3A, + 0x5F, 0x07, 0x9B, 0x07, 0x41, 0xA5, 0xE6, 0xD5, 0x10, 0xE5, 0x87, 0x32, 0xDC, 0x03, 0x59, 0xD7, 0x9A, 0x77, 0x41, 0xA3, 0x79, 0x1C, 0xA6, 0x50, 0x4F, 0x07, 0xCA, 0x8A, 0x2C, 0x03, 0x12, 0x71, + 0x18, 0x45, 0x20, 0xEB, 0x76, 0xA0, 0x0B, 0x9B, 0x46, 0x26, 0xDB, 0x37, 0x34, 0x1C, 0x71, 0x80, 0x65, 0xED, 0x95, 0xFE, 0x4C, 0xB0, 0x54, 0xBF, 0xE7, 0x1E, 0x80, 0x26, 0x0D, 0x21, 0x90, 0x7B, + 0x9B, 0xFA, 0xEC, 0x86, 0xAC, 0x83, 0xA4, 0x85, 0x63, 0xC0, 0xB9, 0xB2, 0xEF, 0x4B, 0x9B, 0x4E, 0xCB, 0xCB, 0x2F, 0x12, 0x91, 0x98, 0x4E, 0x89, 0xE8, 0x4C, 0x55, 0x69, 0x06, 0x47, 0xE2, 0x65, + 0x47, 0xD7, 0x3E, 0x4C, 0xB7, 0xF0, 0xE0, 0x6E, 0xFF, 0xC3, 0xC4, 0x79, 0xE2, 0x56, 0x8E, 0x74, 0x64, 0xEA, 0xBF, 0x1D, 0x1C, 0x4E, 0xFE, 0x21, 0x11, 0x12, 0xE6, 0x2B, 0xEA, 0x8B, 0x85, 0x5F, + 0x50, 0xD7, 0x16, 0x51, 0x32, 0x9C, 0x00, 0xEF, 0x61, 0x9F, 0x53, 0x7E, 0x45, 0x4B, 0x09, 0x5A, 0x9D, 0xF6, 0xA8, 0x59, 0x0E, 0x5B, 0xBA, 0xA1, 0x5C, 0x9E, 0x64, 0xE7, 0x01, 0xE3, 0x74, 0x69, + 0x74, 0x94, 0x62, 0xA2, 0x11, 0x95, 0x41, 0xE7, 0x55, 0x49, 0xD0, 0x56, 0xA2, 0x5B, 0xBC, 0xEE, 0x11, 0xCD, 0x9F, 0xC6, 0x72, 0x42, 0x2A, 0xD2, 0xAE, 0x97, 0x91, 0x3D, 0x30, 0xBE, 0x3C, 0xD8, + 0x5F, 0x58, 0xCF, 0xA9, 0x04, 0xF4, 0x43, 0xAC, 0x3A, 0x8D, 0xFD, 0xBC, 0x2C, 0xC9, 0xC8, 0xC3, 0x9B, 0x24, 0x4E, 0xE7, 0xE0, 0xD9, 0x5B, 0xEC, 0x69, 0x27, 0xA2, 0xB0, 0xB9, 0x4E, 0x97, 0x3F, + 0x98, 0x12, 0x24, 0x46, 0x43, 0x14, 0x6E, 0x19, 0x01, 0x3B, 0x7F, 0xE1, 0x71, 0x14, 0xA0, 0xF3, 0x9F, 0x92, 0x28, 0x6B, 0xE0, 0xF0, 0xEE, 0x39, 0x6F, 0xB7, 0x4C, 0x76, 0xC9, 0x10, 0x04, 0xB8, + 0x27, 0xD2, 0x18, 0x95, 0x1C, 0x77, 0xBD, 0xB8, 0x15, 0x90, 0xAE, 0xDF, 0xEA, 0x9E, 0x62, 0xBE, 0x0F, 0x22, 0xAF, 0xF5, 0x5E, 0x36, 0xAB, 0x57, 0x2D, 0xF1, 0x3A, 0xB9, 0xF5, 0xEA, 0xFC, 0xBC, + 0x34, 0xDF, 0x26, 0x6F, 0xE1, 0x60, 0xC6, 0xB6, 0x35, 0xB0, 0xC3, 0xB6, 0x3C, 0x89, 0x29, 0x20, 0x18, 0x5F, 0x11, 0x2B, 0x96, 0x99, 0x8B, 0x5B, 0x5B, 0xB9, 0x73, 0xB3, 0x90, 0x08, 0xB2, 0xF0, + 0x43, 0x40, 0x35, 0xD4, 0x3B, 0xD2, 0xE4, 0x9F, 0x2C, 0x17, 0x45, 0x20, 0xD3, 0xA8, 0x98, 0x54, 0xCD, 0x82, 0x50, 0xD6, 0x20, 0x0A, 0x1E, 0xB5, 0x10, 0x79, 0x22, 0x46, 0x56, 0xD0, 0xB3, 0x34, + 0xCE, 0xE3, 0x43, 0x0B, 0x87, 0xE1, 0xFF, 0x90, 0x4D, 0x10, 0x34, 0xC2, 0xD8, 0xA7, 0x04, 0x7B, 0x2D, 0x22, 0x56, 0x33, 0x19, 0x04, 0x10, 0x01, 0x2C, 0x16, 0x1C, 0x76, 0x8C, 0x1F, 0xF8, 0xFC, + 0x17, 0x9A, 0x44, 0x68, 0x64, 0xDF, 0x93, 0xE0, 0x9D, 0x1E, 0x6C, 0x29, 0x48, 0x7C, 0xAB, 0x04, 0x4E, 0xF8, 0x68, 0xD4, 0x31, 0xB1, 0x76, 0x31, 0x84, 0xAD, 0xCB, 0x39, 0x51, 0x6D, 0xD1, 0x27, + 0x6B, 0xD8, 0x41, 0xEC, 0x49, 0x2A, 0x84, 0x51, 0x77, 0x4E, 0xDA, 0x10, 0x6E, 0x73, 0x21, 0xED, 0x5A, 0x62, 0x25, 0xC3, 0x53, 0x24, 0xC5, 0x10, 0x66, 0x3B, 0x9B, 0xEA, 0x05, 0xF1, 0xDB, 0xC8, + 0xD5, 0xDB, 0x69, 0xA7, 0x7E, 0xCE, 0x3E, 0x42, 0x65, 0xC5, 0xE8, 0x10, 0x69, 0x86, 0x45, 0x80, 0xB5, 0x28, 0xCC, 0x2C, 0xBB, 0xFB, 0xDE, 0x62, 0x5A, 0xF2, 0xC1, 0xC5, 0xCB, 0x06, 0xDD, 0x80, + 0x58, 0x54, 0x04, 0x96, 0x4D, 0x21, 0x11, 0x4B, 0x8B, 0x13, 0xCA, 0xFB, 0x6D, 0xBE, 0x1B, 0x42, 0x8E, 0xBC, 0x87, 0x17, 0xCC, 0xD1, 0x1B, 0xFB, 0x34, 0x72, 0x60, 0xAA, 0x70, 0x1B, 0xF2, 0x28, + 0x35, 0xB3, 0xF1, 0x06, 0x2E, 0xAD, 0x36, 0xAC, 0xB9, 0x6D, 0x74, 0x96, 0xF7, 0x2A, 0xA5, 0xFF, 0x1A, 0x13, 0x04, 0xBC, 0x02, 0xE3, 0x58, 0xE6, 0x0B, 0x1C, 0x82, 0x30, 0xBF, 0x8F, 0xFA, 0xFD, + 0x36, 0xE0, 0xF6, 0xB2, 0xE3, 0xD8, 0x58, 0x2F, 0xD3, 0xA4, 0x38, 0x11, 0xAC, 0x24, 0xD0, 0x60, 0x08, 0x10, 0x35, 0x42, 0x87, 0x8C, 0xB5, 0xCE, 0x99, 0xF8, 0x92, 0x0C, 0xC8, 0x02, 0xDA, 0x4E, + 0xD2, 0x18, 0x39, 0x56, 0x83, 0x4D, 0xA4, 0xC7, 0x19, 0x55, 0x0D, 0xB2, 0x47, 0x95, 0xAC, 0xE0, 0x9D, 0x88, 0xCA, 0x30, 0x43, 0xAF, 0xCC, 0xC9, 0xAB, 0x0F, 0x03, 0x06, 0x67, 0x1F, 0xD1, 0xF2, + 0x50, 0x95, 0x7C, 0xC6, 0x24, 0x64, 0xC9, 0xEA, 0x5E, 0x44, 0x4C, 0x6E, 0xB4, 0x76, 0xD0, 0x92, 0x46, 0x56, 0x08, 0xFE, 0xB6, 0xB7, 0xD5, 0x39, 0x8A, 0x02, 0x9E, 0x1E, 0xEA, 0xE5, 0x0D, 0xB5, + 0xF9, 0xF9, 0x95, 0x50, 0xA9, 0x66, 0x83, 0x43, 0xEF, 0x29, 0x70, 0xF2, 0x25, 0x31, 0x67, 0x8E, 0x36, 0x71, 0x3B, 0x81, 0xCB, 0x36, 0x33, 0xF1, 0xDD, 0xD4, 0x67, 0x69, 0x82, 0x6E, 0x43, 0x60, + 0xDE, 0x19, 0xA5, 0x63, 0x18, 0xD9, 0xEB, 0x59, 0xF9, 0x7A, 0x9B, 0x3E, 0xD2, 0x2B, 0xFD, 0x89, 0x50, 0x11, 0x26, 0x29, 0x5E, 0x89, 0xFC, 0x73, 0x5C, 0x36, 0x19, 0xD7, 0x7F, 0x6F, 0xB9, 0x35, + 0xC2, 0xFB, 0x46, 0xED, 0xD0, 0xA4, 0xD2, 0x92, 0x17, 0x77, 0xB0, 0xEF, 0xCD, 0x58, 0xBE, 0xDC, 0xEB, 0x9E, 0xA5, 0x66, 0x6B, 0x18, 0xDF, 0xAC, 0xF9, 0xBF, 0x76, 0x33, 0x3C, 0x5E, 0xDA, 0xC7, + 0x2B, 0x04, 0xE6, 0x57, 0xE4, 0xE0, 0x86, 0x5E, 0x04, 0x3A, 0x64, 0x68, 0xC5, 0xE6, 0x9D, 0x5B, 0xCB, 0xE5, 0x84, 0x2B, 0xF4, 0x5B, 0xEE, 0x77, 0x91, 0x5F, 0x05, 0x71, 0xD1, 0x50, 0xD6, 0x06, + 0xA6, 0xF2, 0xAC, 0x37, 0x37, 0x92, 0x90, 0x88, 0x91, 0xBA, 0x85, 0xF4, 0x5C, 0xB4, 0x09, 0xD9, 0x63, 0xE4, 0x9B, 0x5B, 0x96, 0x97, 0x8A, 0x19, 0x39, 0x16, 0x0A, 0x8D, 0xB9, 0xD6, 0x3C, 0x4E, + 0xA0, 0xD6, 0xA7, 0xD0, 0x93, 0x70, 0xAC, 0x1C, 0x24, 0x49, 0x8D, 0x21, 0xA8, 0xD5, 0xB7, 0x64, 0xA3, 0x9A, 0x41, 0x2E, 0x5B, 0x54, 0xBD, 0x1C, 0x96, 0x4D, 0x24, 0x4A, 0x45, 0x55, 0x64, 0x5F, + 0x1F, 0x90, 0x53, 0xF8, 0xBB, 0x33, 0xF6, 0xF7, 0x51, 0x46, 0x80, 0x7B, 0x4E, 0x9E, 0x07, 0xB2, 0x3C, 0x98, 0x06, 0xFF, 0x75, 0x72, 0x46, 0x9C, 0x09, 0x43, 0x99, 0xBA, 0x97, 0x79, 0xB9, 0x62, + 0xB4, 0xC8, 0xA9, 0x57, 0xF8, 0x69, 0x91, 0x1E, 0xB1, 0x3F, 0x14, 0x02, 0x24, 0xAC, 0x4E, 0xE7, 0x62, 0x01, 0xC0, 0x2F, 0x24, 0xC7, 0xED, 0xC3, 0xA9, 0x80, 0x89, 0x9A, 0x30, 0xBA, 0xD2, 0xB1, + 0x2D, 0x57, 0x28, 0xF0, 0x97, 0x17, 0x6D, 0x00, 0x17, 0xF3, 0x47, 0x3D, 0x2F, 0xBB, 0xD4, 0x3C, 0xC2, 0x3A, 0x50, 0x1E, 0x81, 0xE3, 0x81, 0xBE, 0x01, 0x79, 0xBF, 0x68, 0xCA, 0x50, 0xFD, 0x23, + 0x55, 0xCA, 0x7B, 0x64, 0xF5, 0x3E, 0x0C, 0x7D, 0x5B, 0xCA, 0x4E, 0x7B, 0xE6, 0x91, 0x63, 0xE3, 0x16, 0xFE, 0xBB, 0x49, 0xA9, 0x34, 0x0F, 0x15, 0x7B, 0xAC, 0x3B, 0x0B, 0xD8, 0x4A, 0x3B, 0x02, + 0x7A, 0x2F, 0xE4, 0x4E, 0xC2, 0x66, 0xA8, 0xCE, 0x4A, 0x17, 0x1B, 0x91, 0x82, 0x8F, 0x45, 0x43, 0x02, 0xAA, 0x9B, 0x66, 0x49, 0x67, 0xE6, 0x7D, 0xB3, 0x8A, 0xA4, 0xE3, 0xBC, 0x35, 0x3D, 0x15, + 0x18, 0xA7, 0xFE, 0xC1, 0x18, 0x8B, 0x7D, 0x5B, 0x7E, 0x19, 0x52, 0x1F, 0x1A, 0x28, 0x77, 0x00, 0x69, 0x89, 0xB0, 0xFE, 0x91, 0x89, 0x46, 0xB7, 0x59, 0x3E, 0xD1, 0x51, 0x20, 0xBF, 0x7D, 0x23, + 0xF9, 0x92, 0x10, 0xDD, 0xB7, 0x6D, 0xAF, 0x86, 0xE2, 0x37, 0xB2, 0x37, 0x9C, 0xA1, 0x2E, 0x55, 0x63, 0x6C, 0x83, 0x40, 0x8E, 0x6D, 0x2B, 0x35, 0x85, 0xFA, 0xBC, 0xBC, 0x0F, 0x6C, 0x48, 0x76, + 0x7E, 0x36, 0x3A, 0xC8, 0x47, 0xCC, 0xC6, 0x7E, 0xB7, 0xC9, 0x37, 0xBB, 0xD9, 0x41, 0x10, 0x0D, 0x78, 0x77, 0x4A, 0xE1, 0xF4, 0x43, 0x39, 0xDC, 0xDC, 0xB0, 0xE7, 0x00, 0xAC, 0x10, 0x8D, 0xAA, + 0x92, 0xCD, 0x9E, 0xA1, 0x9F, 0x82, 0x38, 0xF2, 0x86, 0x76, 0xFE, 0xE7, 0xBD, 0x1B, 0x9F, 0x37, 0xA6, 0xCA, 0x17, 0xD7, 0xCF, 0x40, 0x42, 0xFE, 0x39, 0xDD, 0x93, 0x77, 0x82, 0x6C, 0x4C, 0xAB, + 0x29, 0x32, 0xE1, 0x2D, 0xE5, 0x3B, 0x08, 0x1A, 0x6C, 0x25, 0xC0, 0xF4, 0x7D, 0xA3, 0xD9, 0x16, 0x83, 0x1E, 0x42, 0x47, 0xD0, 0x97, 0x81, 0x1E, 0x1A, 0x08, 0x70, 0xCB, 0x61, 0xF4, 0xAC, 0xA1, + 0x27, 0xEA, 0xF8, 0x5A, 0x9C, 0xA6, 0x66, 0xFA, 0x6C, 0x36, 0x39, 0x8F, 0x0E, 0x74, 0x20, 0xCA, 0x98, 0x95, 0xC6, 0x3A, 0x1A, 0xC4, 0xDB, 0x49, 0xA1, 0xD7, 0x5F, 0x56, 0x46, 0x4C, 0x1E, 0x0C, + 0xF9, 0x28, 0x3A, 0x45, 0x44, 0x56, 0x50, 0xF9, 0x5F, 0xAD, 0xF6, 0xC8, 0x8D, 0xB3, 0xCE, 0x7C, 0x0E, 0x5D, 0x0E, 0x72, 0x61, 0xE8, 0x04, 0xC0, 0x3A, 0x41, 0x9E, 0x4C, 0xC2, 0x50, 0x10, 0x99, + 0xCA, 0x53, 0x63, 0x44, 0x60, 0x7B, 0x07, 0xE8, 0x25, 0x32, 0x3A, 0xD3, 0x0B, 0xE7, 0x5F, 0x84, 0xE6, 0xC5, 0xBE, 0x23, 0x8E, 0xC7, 0x86, 0x17, 0xA0, 0xA2, 0x34, 0x14, 0xC7, 0xF8, 0xCD, 0x60, + 0x91, 0x30, 0x31, 0xBC, 0x93, 0x01, 0x78, 0x6D, 0x5C, 0x19, 0xD9, 0x30, 0xB5, 0x06, 0xC4, 0x95, 0x98, 0x32, 0x23, 0xEC, 0x1B, 0xF7, 0x87, 0xC3, 0x3D, 0x22, 0x8A, 0x11, 0x0E, 0x57, 0x42, 0x87, + 0x73, 0xE3, 0x4F, 0x12, 0x66, 0x3D, 0x11, 0xC1, 0x55, 0xDF, 0xCE, 0x38, 0x0D, 0x65, 0x76, 0x4C, 0x26, 0x59, 0xEA, 0xA0, 0xA1, 0xA2, 0xE7, 0x64, 0xEB, 0xB5, 0xA9, 0xE5, 0xA7, 0x19, 0x2E, 0x90, + 0x86, 0xA6, 0xDE, 0x4A, 0x38, 0xFC, 0xFD, 0x04, 0x12, 0x42, 0x42, 0x60, 0x62, 0x0C, 0x1E, 0x56, 0x7A, 0x2D, 0x8B, 0x1A, 0xF3, 0x55, 0x48, 0x19, 0xA0, 0x0D, 0x5C, 0x7E, 0x56, 0x66, 0xD0, 0xE6, + 0x56, 0xF8, 0xD4, 0x5C, 0x67, 0xC5, 0x44, 0x8D, 0xAB, 0x5E, 0xB6, 0xE6, 0x02, 0x93, 0x79, 0xC4, 0x7A, 0x24, 0xD0, 0x11, 0xF5, 0x6E, 0x5F, 0xAA, 0x49, 0xFC, 0x6B, 0xB2, 0xD7, 0x50, 0xED, 0x4C, + 0x95, 0xF8, 0x35, 0x38, 0x4F, 0x2F, 0xAA, 0xB1, 0x3C, 0x1C, 0xCA, 0x71, 0xA1, 0xEB, 0xD2, 0x29, 0x9E, 0x96, 0x32, 0xE5, 0x29, 0xCE, 0x77, 0x14, 0x9F, 0x5F, 0xAC, 0x31, 0xAB, 0x28, 0xDC, 0xC7, + 0x06, 0x70, 0xBB, 0xAB, 0x9F, 0x7B, 0x6F, 0xFE, 0xAA, 0xBC, 0x7D, 0xC4, 0x51, 0x3D, 0x8F, 0xAC, 0x4B, 0xCF, 0x7E, 0x5E, 0x72, 0x97, 0xDB, 0x69, 0xE4, 0xB6, 0x25, 0x38, 0xF9, 0xCA, 0xBD, 0x90, + 0x2B, 0x10, 0x07, 0xE3, 0xBA, 0xF6, 0x7F, 0x94, 0x3D, 0xFD, 0xC6, 0xAA, 0x75, 0x62, 0xFA, 0xBB, 0x1E, 0x8F, 0xAC, 0xF8, 0x11, 0xC7, 0x63, 0x35, 0x79, 0x0A, 0x16, 0xF2, 0x1E, 0xCB, 0x72, 0xFC, + 0x1B, 0xA9, 0x42, 0x76, 0xB2, 0x09, 0x80, 0x7E, 0xA5, 0x2E, 0x74, 0xF2, 0xB6, 0xCA, 0x0B, 0x3F, 0xDC, 0x30, 0x50, 0x1F, 0x63, 0x10, 0xEC, 0x99, 0x55, 0xB0, 0x51, 0x81, 0x8D, 0xAE, 0x10, 0x80, + 0xFD, 0x4D, 0xD2, 0x4C, 0x72, 0x2D, 0x68, 0xDE, 0x33, 0xEA, 0x76, 0x9B, 0x4E, 0x63, 0x70, 0x07, 0xCF, 0xDC, 0xE1, 0x80, 0x4A, 0xC2, 0xA7, 0x71, 0xF8, 0x8F, 0x59, 0xBA, 0xCE, 0xDB, 0x4D, 0xFB, + 0x79, 0xA4, 0x1E, 0xA7, 0x0F, 0x14, 0xAC, 0xCE, 0x6A, 0x5A, 0x8A, 0x88, 0x43, 0xB5, 0x95, 0x89, 0xE4, 0x52, 0x8B, 0xA8, 0x52, 0x10, 0x42, 0x1D, 0x1E, 0x59, 0x5F, 0x84, 0xC2, 0x75, 0x90, 0x47, + 0xDB, 0x47, 0x22, 0x26, 0x73, 0x86, 0x8C, 0x00, 0x27, 0xEE, 0xFD, 0x99, 0x6E, 0xF8, 0xC8, 0xC4, 0xF3, 0x67, 0xA9, 0x1D, 0xEC, 0xF1, 0x79, 0x43, 0x22, 0x7D, 0x4D, 0x00, 0x44, 0x7F, 0xFC, 0x6C, + 0xC8, 0x66, 0x5E, 0x08, 0xD2, 0x93, 0xA4, 0xDE, 0x4E, 0xE1, 0x15, 0x69, 0xB9, 0x5B, 0xB4, 0xDA, 0xE7, 0x58, 0x15, 0x0E, 0x55, 0x78, 0x32, 0x55, 0xE2, 0xF3, 0x22, 0x27, 0xB4, 0x5A, 0x9D, 0x26, + 0x19, 0x77, 0x1C, 0xED, 0x51, 0x2D, 0x5C, 0xD8, 0x90, 0x18, 0xC9, 0x9E, 0x2F, 0x05, 0x23, 0x3E, 0xF5, 0x86, 0x0F, 0xEC, 0xB3, 0x79, 0x1B, 0x53, 0xAD, 0x2C, 0x22, 0x8A, 0xBA, 0xBB, 0x9F, 0xD1, + 0xF5, 0x04, 0x38, 0xE9, 0xB0, 0xC6, 0xEA, 0x61, 0xE2, 0x0B, 0xB5, 0xAC, 0x0A, 0xAD, 0x30, 0x50, 0x9F, 0xEA, 0x9A, 0x44, 0x1D, 0x55, 0x5C, 0xDD, 0x34, 0x50, 0x9C, 0xFC, 0x60, 0x62, 0xE6, 0xB8, + 0x1D, 0xCA, 0xCF, 0xD5, 0xF5, 0xC9, 0xC5, 0x26, 0xB3, 0x8D, 0x70, 0x4C, 0x1F, 0x0F, 0x28, 0xB4, 0xFB, 0x7C, 0x1A, 0xC6, 0x9A, 0xA1, 0x96, 0xCF, 0x81, 0x2E, 0x44, 0x46, 0xEF, 0x68, 0x02, 0x87, + 0x44, 0xD2, 0xA5, 0x40, 0xFA, 0x7A, 0x69, 0xCF, 0x87, 0xA1, 0xF9, 0x68, 0x24, 0xE4, 0xC6, 0x87, 0x82, 0x35, 0xF0, 0xCC, 0xA3, 0xE9, 0x7B, 0x2B, 0x22, 0xB0, 0x93, 0xD9, 0x5E, 0xE1, 0x8D, 0xBF, + 0xE6, 0x76, 0x1D, 0xFA, 0xF8, 0x34, 0x47, 0x51, 0x86, 0x07, 0x56, 0x02, 0x31, 0x3E, 0xE2, 0xA2, 0x99, 0xBC, 0xCC, 0xC6, 0x53, 0x1E, 0xDA, 0x54, 0x10, 0xCC, 0xFA, 0x09, 0xEC, 0xB8, 0xA6, 0x0D, + 0x28, 0x33, 0x7A, 0xA5, 0x56, 0x58, 0x6D, 0x78, 0x48, 0x49, 0x38, 0x0F, 0x02, 0xEB, 0xB8, 0x37, 0xCB, 0x0B, 0xDE, 0x57, 0xBB, 0xA9, 0x07, 0xB6, 0x7C, 0x7A, 0xD8, 0x66, 0xE1, 0xDD, 0xB1, 0xC7, + 0x9D, 0x96, 0x1D, 0x70, 0xF5, 0x5D, 0x05, 0x9A, 0xCF, 0xD3, 0x9F, 0x5B, 0xD3, 0x03, 0x74, 0xB4, 0x84, 0x5E, 0x04, 0xEC, 0x26, 0xE8, 0xB5, 0xB9, 0x3F, 0xC4, 0x54, 0x4F, 0x24, 0xAE, 0x99, 0xC9, + 0xE5, 0x1E, 0x43, 0x57, 0x75, 0xD2, 0x20, 0x80, 0xE1, 0x9E, 0x3A, 0xC2, 0x25, 0xC7, 0xE1, 0xEE, 0x0A, 0x56, 0xB9, 0x52, 0x30, 0x7F, 0x44, 0xBA, 0xCF, 0x4C, 0x87, 0x85, 0x35, 0x5C, 0x09, 0xDB, + 0xD0, 0xD8, 0x60, 0x57, 0xF0, 0xA6, 0xA9, 0x88, 0xC3, 0x65, 0x74, 0x20, 0x25, 0x19, 0xDE, 0xBA, 0x04, 0x56, 0x98, 0xD7, 0x24, 0x27, 0x77, 0x0C, 0x37, 0x31, 0xC9, 0xB7, 0x53, 0x5F, 0xAA, 0xF0, + 0xCC, 0xA9, 0xD1, 0x3C, 0x42, 0x12, 0xB7, 0x62, 0x94, 0x57, 0x52, 0xE7, 0xA6, 0x53, 0x9B, 0x47, 0xBE, 0xA9, 0x66, 0x48, 0x23, 0x18, 0xA9, 0xCF, 0xE3, 0xBA, 0xEC, 0x6A, 0x83, 0xFB, 0x34, 0xF0, + 0xB6, 0x8E, 0xE9, 0x77, 0x97, 0x42, 0x0F, 0xAD, 0xC3, 0xF0, 0x25, 0xEE, 0x9F, 0x18, 0xBE, 0xA3, 0x8F, 0xBE, 0xC0, 0xC5, 0xDE, 0xAA, 0xC7, 0xA5, 0x2F, 0x7E, 0xB8, 0xD9, 0x4F, 0xE4, 0xC6, 0x62, + 0x54, 0x14, 0x57, 0xA1, 0x53, 0x82, 0x4B, 0xE6, 0x0D, 0x7D, 0xB8, 0x33, 0x89, 0x0F, 0x3A, 0xC3, 0xF7, 0xBD, 0x6D, 0x73, 0xF8, 0x0C, 0x67, 0x2B, 0x76, 0xA5, 0x26, 0x7D, 0xF2, 0x2C, 0xFB, 0x5E, + 0x1B, 0x92, 0xB0, 0xCD, 0x68, 0xE9, 0xA9, 0x20, 0x92, 0x43, 0xA4, 0x2A, 0x30, 0xF7, 0xAA, 0x1F, 0x03, 0xD0, 0xD9, 0x11, 0x3F, 0x04, 0xB7, 0x6E, 0xB5, 0xAA, 0x69, 0xBC, 0x9B, 0x8F, 0xE7, 0x98, + 0xE7, 0x75, 0x01, 0xB0, 0x56, 0x30, 0x29, 0xF5, 0x02, 0xF7, 0x79, 0x4D, 0xD3, 0x90, 0x74, 0x7A, 0xED, 0x08, 0x5C, 0x22, 0xB2, 0x16, 0x11, 0xA9, 0xC7, 0x62, 0x38, 0xEF, 0x65, 0x84, 0xAE, 0xFB, + 0xB3, 0x57, 0xF8, 0x36, 0x25, 0x86, 0xC5, 0x9F, 0xCA, 0x8E, 0x09, 0x26, 0x10, 0x11, 0x5F, 0x4D, 0xC2, 0x93, 0x0D, 0x72, 0x24, 0x28, 0x5E, 0xB8, 0xFD, 0x99, 0x2F, 0x82, 0x17, 0xAE, 0x94, 0x70, + 0xA7, 0x4A, 0xE3, 0xE8, 0x06, 0x01, 0x0C, 0x8D, 0x02, 0x19, 0x48, 0xBE, 0x57, 0xAB, 0x1D, 0x62, 0xC0, 0x41, 0x2E, 0xA5, 0xC9, 0x69, 0xD0, 0x56, 0x68, 0x41, 0xF2, 0xE2, 0x56, 0x8E, 0x01, 0x33, + 0x64, 0xD8, 0x7C, 0xAF, 0x33, 0x22, 0x9D, 0x2A, 0xA6, 0xC5, 0x6B, 0x9F, 0xB4, 0xC1, 0x36, 0xA1, 0x3F, 0x5E, 0x73, 0x3A, 0x91, 0xEF, 0xF2, 0x1D, 0xCB, 0x29, 0x0D, 0x8E, 0xC6, 0xDC, 0x0A, 0x50, + 0xE5, 0x7C, 0x1F, 0x65, 0xEB, 0x2B, 0xA1, 0xC3, 0x9D, 0xDB, 0x1C, 0x09, 0x54, 0x24, 0xE6, 0xF4, 0x1F, 0x9E, 0x86, 0x56, 0x7F, 0x91, 0x14, 0x00, 0xD8, 0x5C, 0x90, 0xD6, 0x4F, 0xC7, 0xE6, 0xEC, + 0xC2, 0x88, 0x04, 0xF2, 0x70, 0x42, 0x40, 0x24, 0x9E, 0xFC, 0x8F, 0xEC, 0x69, 0xE3, 0x66, 0xF3, 0x68, 0x7A, 0x76, 0x20, 0x5C, 0x0D, 0x1D, 0xD6, 0x48, 0x39, 0x12, 0xA8, 0xF6, 0x8E, 0xAE, 0x2C, + 0xB3, 0x52, 0x0A, 0x8B, 0x17, 0x2C, 0xF2, 0xCD, 0x2B, 0x03, 0x80, 0x2E, 0x5F, 0xA7, 0xB1, 0xF1, 0xEF, 0x8C, 0xA0, 0xA6, 0x08, 0x0B, 0xF9, 0xDA, 0x37, 0x82, 0xD2, 0xBD, 0xE4, 0xB3, 0xA3, 0xC6, + 0x5C, 0xFB, 0x9F, 0x1B, 0x39, 0x05, 0xB9, 0x36, 0x1D, 0x1E, 0x0C, 0x8F, 0xEB, 0x5A, 0xB4, 0x0A, 0x3F, 0xFE, 0xB3, 0xAE, 0x95, 0xF5, 0x75, 0x62, 0xA0, 0x7C, 0xD2, 0x43, 0x18, 0xC0, 0xE7, 0xEE, + 0x6E, 0xBE, 0x57, 0x0C, 0xB7, 0xDC, 0x1C, 0x62, 0x1A, 0x84, 0x92, 0x13, 0xE7, 0x13, 0x92, 0x42, 0x75, 0x81, 0x28, 0xC1, 0x6C, 0xFE, 0x52, 0xF8, 0xE2, 0xED, 0xA5, 0xBA, 0x23, 0x23, 0x15, 0x6F, + 0x85, 0x3A, 0xBC, 0x61, 0xB1, 0x39, 0x04, 0x1A, 0x4B, 0x83, 0x40, 0x37, 0xAA, 0x19, 0xDC, 0xEE, 0x76, 0x06, 0xAE, 0x84, 0xC1, 0xA7, 0x4D, 0x0E, 0xEB, 0x6A, 0x4D, 0xAB, 0xD5, 0x90, 0x8D, 0xAE, + 0x2C, 0x23, 0xA6, 0x38, 0x76, 0xE7, 0xE9, 0xF8, 0xE9, 0x03, 0x66, 0xA1, 0xFD, 0x89, 0xF2, 0x28, 0x3D, 0x75, 0x30, 0x09, 0xE0, 0x56, 0xDD, 0x5A, 0xB9, 0x53, 0xDB, 0x3D, 0x8F, 0x48, 0x30, 0xA4, + 0xD0, 0x93, 0x79, 0x39, 0x5F, 0x21, 0xED, 0x03, 0xB6, 0xCC, 0xD5, 0xD7, 0xF8, 0xF8, 0x1F, 0x40, 0x0B, 0x3E, 0x3B, 0xC6, 0x96, 0x08, 0x8D, 0x58, 0x17, 0x75, 0x21, 0x11, 0x0B, 0x6C, 0x84, 0x74, + 0xF3, 0xE4, 0x49, 0xD8, 0xEC, 0x7F, 0x46, 0x6C, 0x2E, 0xB3, 0x43, 0x65, 0x9F, 0xF5, 0x33, 0x97, 0x58, 0x7B, 0xC6, 0x30, 0x0D, 0xEE, 0xBD, 0xC2, 0xBE, 0x67, 0x4B, 0x78, 0x30, 0x90, 0xEA, 0xCC, + 0xB9, 0x3B, 0x6A, 0xE9, 0x49, 0x56, 0xA3, 0x33, 0xE8, 0x58, 0x37, 0x64, 0x73, 0xCA, 0x67, 0xAF, 0x05, 0x43, 0xE5, 0x99, 0x94, 0x1E, 0xB4, 0xE8, 0xC6, 0xD9, 0x5D, 0x47, 0x9F, 0xEE, 0xE0, 0x5E, + 0x3E, 0x8B, 0xF5, 0xF0, 0xAA, 0xCD, 0x34, 0x51, 0xC0, 0xED, 0x48, 0x1F, 0x52, 0x6D, 0x38, 0xEB, 0x3B, 0x26, 0xA4, 0xFD, 0x98, 0xE1, 0x1B, 0xAF, 0x67, 0xED, 0xEA, 0xB2, 0xEC, 0xC7, 0xD3, 0x97, + 0xE9, 0x68, 0xF8, 0xD1, 0x03, 0xE8, 0x01, 0x44, 0xA4, 0xCD, 0xB7, 0x00, 0xC4, 0x1A, 0x42, 0x83, 0x4B, 0x07, 0xFD, 0x7E, 0x91, 0xF3, 0xC5, 0x24, 0x09, 0xC6, 0x88, 0x2C, 0xF4, 0x15, 0xA4, 0x2F, + 0x71, 0xE2, 0x1F, 0xE7, 0x00, 0x17, 0xD6, 0x2B, 0x1F, 0xE4, 0x3A, 0x2A, 0x32, 0xD8, 0x15, 0xE3, 0xF1, 0xA4, 0x4E, 0x72, 0x67, 0xB1, 0xBB, 0xF5, 0x52, 0xF3, 0x8E, 0x88, 0x97, 0x75, 0xEC, 0xD8, + 0x5C, 0x4B, 0xF4, 0x65, 0x02, 0x22, 0xF3, 0x30, 0xFA, 0xE4, 0xB6, 0x17, 0x65, 0x52, 0x54, 0x03, 0xFB, 0xDE, 0x0A, 0x18, 0xF9, 0x73, 0x65, 0x7C, 0xAB, 0xEB, 0x05, 0xFE, 0x6B, 0x97, 0x29, 0xD3, + 0xB3, 0x73, 0x0A, 0xEF, 0xDF, 0x3C, 0x18, 0x96, 0x99, 0x7A, 0x94, 0x9B, 0x60, 0x3C, 0x43, 0xFE, 0xCC, 0x3E, 0xAC, 0xCB, 0xF0, 0x0C, 0x03, 0x76, 0x59, 0x41, 0x80, 0x0C, 0xE4, 0x2F, 0xD0, 0x38, + 0x4E, 0x1C, 0x1C, 0x61, 0x17, 0x31, 0x6C, 0xBA, 0x1A, 0x81, 0xA2, 0x09, 0x03, 0x3C, 0x5B, 0x53, 0xAE, 0x3B, 0x60, 0xBC, 0x1A, 0xFC, 0x6E, 0x7C, 0x95, 0xC5, 0xCB, 0x99, 0xC2, 0x6A, 0x4C, 0x88, + 0x1F, 0x62, 0x6A, 0x21, 0x9A, 0x61, 0x9B, 0xC3, 0x5C, 0xF4, 0xEF, 0x0A, 0x3B, 0x67, 0x25, 0x34, 0x9D, 0x2C, 0x13, 0xD8, 0x9D, 0xE6, 0x5D, 0x9F, 0x7A, 0x35, 0x51, 0xCC, 0xCF, 0xC5, 0x61, 0x1D, + 0xC9, 0xC8, 0x73, 0x7B, 0x0E, 0xF0, 0xFA, 0xDF, 0x86, 0x5A, 0x65, 0x33, 0x9F, 0x46, 0x4C, 0xB0, 0x65, 0xBA, 0x8F, 0xE4, 0x81, 0x06, 0x46, 0xA3, 0x44, 0x5B, 0x70, 0x2F, 0x51, 0xD6, 0xA9, 0x13, + 0x49, 0xFD, 0x70, 0xA3, 0x56, 0x49, 0xFD, 0x4D, 0xAE, 0xE6, 0x13, 0x10, 0xA3, 0xCC, 0xA5, 0xED, 0x3A, 0xBD, 0xBF, 0xF8, 0x35, 0x5B, 0x51, 0x14, 0x83, 0x5F, 0xDE, 0x73, 0xC9, 0xF5, 0x2A, 0xC2, + 0x29, 0xB1, 0x5E, 0x84, 0xD3, 0xF5, 0x9D, 0xCB, 0x13, 0x02, 0x55, 0x1E, 0xA4, 0xDD, 0x6F, 0x41, 0x5D, 0x01, 0x39, 0x11, 0xD6, 0x53, 0x15, 0xC8, 0xE5, 0x9B, 0x12, 0x20, 0x4A, 0xAA, 0xF5, 0x25, + 0x75, 0x4E, 0x96, 0xEC, 0x3C, 0xB1, 0x3E, 0x19, 0x72, 0x62, 0x1F, 0x9C, 0x86, 0xF5, 0xDE, 0x4A, 0xDA, 0xB9, 0x80, 0xCF, 0x83, 0x69, 0x12, 0x7C, 0x2B, 0x3E, 0x4E, 0xF1, 0xA8, 0x2B, 0x7A, 0xC9, + 0x59, 0xAB, 0x45, 0xD9, 0x7E, 0xEE, 0x7A, 0x14, 0xE4, 0x14, 0x5B, 0x34, 0x9B, 0x53, 0x3D, 0xD9, 0x2D, 0xD2, 0xC1, 0x77, 0xC7, 0x7A, 0xBA, 0x32, 0x5D, 0xD7, 0x5C, 0x77, 0xB3, 0x1A, 0x6A, 0xB3, + 0xAA, 0xBE, 0x54, 0xA6, 0xCF, 0xA2, 0xDC, 0xA3, 0x5E, 0x20, 0x99, 0x35, 0xEF, 0x9D, 0x94, 0x7A, 0x37, 0xE8, 0x35, 0x97, 0xB9, 0x4F, 0xCA, 0xF5, 0x8A, 0x56, 0xD1, 0x4A, 0x05, 0x69, 0x12, 0xC2, + 0x2A, 0x54, 0xA6, 0xFF, 0x2F, 0xE8, 0x25, 0xBA, 0xAD, 0x8A, 0xBF, 0x1D, 0xD8, 0x7F, 0xB0, 0xFA, 0x15, 0x19, 0xA5, 0xB7, 0xB4, 0x2F, 0x4B, 0xB2, 0xF7, 0x57, 0xEF, 0xF7, 0xC1, 0x2A, 0x2C, 0xD1, + 0xB9, 0x1F, 0xAE, 0xBF, 0x80, 0x86, 0x51, 0x6D, 0xCD, 0xD5, 0x5F, 0x63, 0x84, 0x18, 0x8F, 0x53, 0xC6, 0xA7, 0x81, 0x86, 0x2F, 0xB5, 0xCC, 0x3C, 0xC6, 0x1A, 0xDE, 0x2F, 0x11, 0x08, 0xD1, 0x51, + 0x63, 0xC3, 0x8C, 0x4C, 0xA0, 0x1B, 0xF7, 0xF2, 0xC8, 0x1B, 0x8C, 0x79, 0xAD, 0x69, 0x4A, 0x01, 0x61, 0x7B, 0xC0, 0x4F, 0x84, 0x70, 0xC2, 0xC7, 0x71, 0xBE, 0xE2, 0x9A, 0x66, 0x6B, 0xE8, 0x51, + 0x42, 0xCB, 0x96, 0x7E, 0xC5, 0x69, 0xA4, 0x02, 0x2A, 0x64, 0xFC, 0x5D, 0x95, 0xA5, 0x57, 0x76, 0xAC, 0x73, 0x27, 0x55, 0xB2, 0x39, 0x29, 0xF2, 0x59, 0x86, 0xD9, 0x3C, 0x01, 0x9B, 0xBB, 0xFB, + 0x15, 0x4C, 0x26, 0xBB, 0x47, 0xA2, 0xBA, 0x4B, 0x32, 0x97, 0xDC, 0xE4, 0x47, 0xC5, 0x61, 0xA1, 0xC4, 0x9F, 0x75, 0x35, 0xA7, 0xA1, 0x4C, 0x98, 0x30, 0x18, 0x6A, 0xA0, 0xDD, 0xFA, 0x00, 0x1A, + 0xEA, 0x0D, 0x94, 0xC4, 0x0A, 0xC8, 0xA8, 0x41, 0x8E, 0x8D, 0x57, 0x8D, 0x84, 0x21, 0x41, 0x3F, 0xB7, 0xE8, 0x20, 0x23, 0x7E, 0xF3, 0xB5, 0xCB, 0xF6, 0x08, 0x1C, 0x44, 0x2C, 0x13, 0xB4, 0x98, + 0x5E, 0xE6, 0x39, 0xE8, 0xF8, 0x6D, 0xB2, 0x87, 0x3B, 0xC2, 0xC9, 0xD3, 0xA9, 0xE5, 0x17, 0xAD, 0x70, 0x31, 0xDA, 0x3C, 0xC9, 0x2F, 0xC1, 0x5F, 0x50, 0x2F, 0xAD, 0x3F, 0xC5, 0xFD, 0xBB, 0xCD, + 0x2C, 0x95, 0x50, 0xA8, 0x95, 0x25, 0xF0, 0x06, 0x7C, 0xC3, 0xEA, 0x22, 0xD8, 0xD5, 0xB6, 0x1A, 0xFA, 0xA4, 0xB5, 0x53, 0xAC, 0x30, 0x39, 0x20, 0xF2, 0x5D, 0x6D, 0x58, 0xF6, 0x1F, 0x63, 0x56, + 0x68, 0x5E, 0x43, 0x50, 0x9A, 0x00, 0x62, 0xF8, 0x37, 0xBC, 0xB9, 0xA1, 0xA2, 0x2C, 0xFF, 0x08, 0x10, 0x80, 0x18, 0xD6, 0xD2, 0x4B, 0xDC, 0x2B, 0x09, 0x6D, 0x2E, 0xA0, 0x82, 0x0A, 0x05, 0x03, + 0x82, 0x0A, 0x01, 0x00, 0x03, 0x23, 0x69, 0xA2, 0xCE, 0x57, 0x2F, 0xD0, 0x8B, 0xFC, 0x30, 0x4B, 0x48, 0x48, 0xE7, 0x8D, 0x75, 0x2D, 0x77, 0xE9, 0x7A, 0x28, 0xB9, 0x9B, 0x9B, 0xB6, 0xFB, 0x5C, + 0x7C, 0x63, 0x37, 0x51, 0x4B, 0x32, 0x1E, 0xCD, 0xC1, 0xFB, 0x66, 0x9F, 0x26, 0xD4, 0x17, 0x1A, 0xB4, 0x2B, 0x72, 0x72, 0x0E, 0xE7, 0x0E, 0x05, 0x19, 0xA6, 0xE1, 0xD3, 0xD6, 0xD9, 0x91, 0x4E, + 0xC1, 0xB2, 0x1C, 0xDE, 0x38, 0xB4, 0x1A, 0xAC, 0x1D, 0x3A, 0xBE, 0xE6, 0xF2, 0xB7, 0x49, 0x5C, 0x4C, 0x82, 0x0C, 0x1F, 0xC0, 0xCC, 0x9E, 0x71, 0xE2, 0x4C, 0xFB, 0x5C, 0x9C, 0x0D, 0x8E, 0xEF, + 0x42, 0x64, 0xAF, 0x48, 0x4F, 0xAE, 0x4D, 0x6E, 0x5D, 0xDE, 0x65, 0xD4, 0xDF, 0x72, 0xB6, 0x1C, 0x6D, 0xBD, 0x26, 0xF8, 0x61, 0xA5, 0xE0, 0xB8, 0x53, 0xAC, 0x54, 0x13, 0x22, 0x6F, 0xEB, 0xBA, + 0xBA, 0x5E, 0xB4, 0x74, 0xC6, 0xFB, 0x25, 0xA8, 0x26, 0x78, 0xEA, 0x16, 0x06, 0xB4, 0x52, 0xA2, 0x31, 0x12, 0x22, 0x10, 0x17, 0xB8, 0xC0, 0x73, 0xC1, 0x03, 0x78, 0xF9, 0x14, 0x56, 0x41, 0xA8, + 0xC0, 0x78, 0xC0, 0xED, 0x9E, 0x42, 0x16, 0x50, 0xF7, 0x48, 0x89, 0x25, 0x22, 0xAB, 0x9F, 0xB7, 0xD1, 0xFF, 0x8C, 0xF1, 0xCC, 0x71, 0xB8, 0x56, 0x6E, 0x8D, 0xA3, 0x3C, 0xD7, 0x36, 0x17, 0x70, + 0xC0, 0x44, 0x34, 0x9A, 0xC4, 0x40, 0xCC, 0xCD, 0xC6, 0xBB, 0xE3, 0x5E, 0x6C, 0x55, 0x78, 0x27, 0x66, 0xF3, 0x8E, 0x68, 0x8B, 0xF4, 0x78, 0x21, 0x03, 0x72, 0x99, 0xE3, 0x44, 0xEC, 0xDE, 0xCA, + 0x17, 0xAD, 0x5D, 0x15, 0xCD, 0x27, 0xA4, 0xF7, 0xB0, 0x70, 0x66, 0x11, 0x38, 0xED, 0xE8, 0xED, 0x72, 0xA8, 0x95, 0x9C, 0x5A, 0xE3, 0x6B, 0x1C, 0x46, 0x09, 0x4A, 0x53, 0xCB, 0x21, 0xA7, 0xA4, + 0x26, 0x73, 0xF1, 0x40, 0x1C, 0x2B, 0x25, 0x94, 0x94, 0x09, 0x0E, 0x2F, 0x53, 0xD7, 0xEE, 0x70, 0x63, 0x43, 0x1E, 0xE5, 0x85, 0x80, 0x02, 0xD8, 0x50, 0xAF, 0x90, 0x9C, 0x37, 0x83, 0x43, 0x60, + 0x10, 0xF7, 0xEA, 0x88, 0x62, 0x5A, 0x36, 0xA0, 0xF0, 0x18, 0x9F, 0xDE, 0x75, 0xB7, 0xE8, 0xC7, 0xE4, 0xB1, 0x9D, 0x85, 0x27, 0x00, 0x83, 0x28, 0xAD, 0xBC, 0x92, 0x9B, 0xBC, 0x86, 0xE9, 0x64, + 0xCF, 0xC4, 0x8B, 0x8C, 0xF1, 0xDA, 0x5D, 0x7E, 0xD3, 0x33, 0x3A, 0xB5, 0x5C, 0x15, 0x07, 0x28, 0x32, 0x21, 0x4A, 0x77, 0x9A, 0x5F, 0xD1, 0x0C, 0xC0, 0x40, 0x05, 0xF4, 0x6C, 0x1A, 0xA8, 0x88, + 0x4A, 0x16, 0x19, 0x92, 0x47, 0x2F, 0xD5, 0x35, 0xB9, 0x5E, 0xD1, 0x8B, 0xDE, 0x1C, 0x6D, 0x8C, 0xE6, 0x78, 0xD2, 0x81, 0x7D, 0x69, 0xF9, 0x05, 0x71, 0x10, 0x3E, 0x85, 0x20, 0xE7, 0x31, 0x3C, + 0xE7, 0xB9, 0x30, 0xC5, 0xEB, 0xFA, 0xF2, 0xF4, 0xEC, 0x75, 0x8B, 0x62, 0x6B, 0x55, 0x43, 0xA0, 0x68, 0xCD, 0xE0, 0xFD, 0x0E, 0x94, 0xE6, 0xA6, 0x44, 0x75, 0xB2, 0x32, 0x68, 0xBF, 0x03, 0x80, + 0xD0, 0x75, 0x50, 0x8F, 0x85, 0x12, 0x8C, 0xA2, 0x6F, 0x31, 0xA9, 0x0C, 0x4A, 0x7D, 0x28, 0x44, 0x0D, 0x54, 0xD4, 0x06, 0x6B, 0x40, 0x45, 0x88, 0x58, 0x8B, 0x4C, 0xCF, 0x85, 0x0B, 0x97, 0x5C, + 0x73, 0xAF, 0xE6, 0x8C, 0xBC, 0xD1, 0x02, 0x75, 0x5F, 0x61, 0xEB, 0x3E, 0x60, 0x32, 0x3C, 0x57, 0x6E, 0x52, 0x9E, 0xC0, 0xBF, 0x23, 0xBF, 0xA5, 0xBE, 0xA3, 0x9C, 0xB7, 0x3C, 0x37, 0xE8, 0x39, + 0x5D, 0x8D, 0xBD, 0x4C, 0x8D, 0xC8, 0xAB, 0x2F, 0x70, 0xA0, 0xBF, 0xC3, 0xA7, 0x8C, 0x0D, 0x41, 0x3F, 0x08, 0xD1, 0x4D, 0x63, 0x2B, 0xC0, 0x40, 0x3B, 0x03, 0x83, 0xDB, 0xBB, 0x22, 0xBD, 0x9B, + 0x11, 0x3C, 0x89, 0x45, 0x2A, 0xEA, 0xB1, 0x12, 0x10, 0x09, 0x79, 0x47, 0xFE, 0xAA, 0xA3, 0xC9, 0xF0, 0x5D, 0x1D, 0x30, 0x0C, 0x33, 0xA5, 0x5E, 0x3F, 0xBC, 0x81, 0x25, 0x9E, 0x86, 0x27, 0x05, + 0xC3, 0xA1, 0x3B, 0x9E, 0xE3, 0x5F, 0x6B, 0x23, 0xED, 0x10, 0xF4, 0xED, 0xEA, 0x95, 0x19, 0xFA, 0x91, 0xB7, 0xBC, 0xD0, 0xD5, 0x01, 0xB5, 0xED, 0x57, 0xD9, 0x04, 0x9F, 0xAB, 0x91, 0xAA, 0x77, + 0x9C, 0x72, 0x5F, 0xF8, 0xE9, 0xF7, 0x80, 0x17, 0xEA, 0x78, 0x07, 0xFA, 0x25, 0x4B, 0x71, 0x05, 0xE8, 0x26, 0xD0, 0x96, 0xC0, 0x1A, 0xDA, 0xE2, 0xC5, 0xD1, 0x38, 0x25, 0x1A, 0x92, 0xA4, 0x78, + 0xA3, 0x33, 0x73, 0xF4, 0xDE, 0x91, 0x2B, 0x83, 0xB6, 0xFB, 0x4B, 0x0D, 0x0D, 0xE6, 0xBC, 0x11, 0x18, 0xBB, 0x2F, 0xCF, 0xB0, 0x7B, 0xD2, 0x27, 0xA5, 0xF7, 0xF9, 0x91, 0x43, 0x9A, 0x13, 0xDE, + 0x12, 0x38, 0x18, 0x0C, 0xDC, 0x55, 0x11, 0x9E, 0x65, 0xC4, 0x18, 0x58, 0x4D, 0x80, 0x7A, 0x92, 0x6E, 0x4A, 0x9C, 0x0F, 0x70, 0x15, 0x5E, 0xE1, 0x96, 0xFB, 0x07, 0x65, 0x6D, 0x9A, 0xA7, 0x98, + 0x2B, 0x87, 0x95, 0xDB, 0xAD, 0x43, 0xD1, 0x05, 0x9C, 0xA7, 0xF5, 0x80, 0xD3, 0x32, 0x0C, 0x04, 0x38, 0xA5, 0xED, 0x5A, 0x70, 0x32, 0xB2, 0xE9, 0x59, 0x67, 0x84, 0x10, 0xF1, 0x1A, 0xD9, 0x8B, + 0xE8, 0x82, 0x6A, 0x44, 0x26, 0x26, 0x15, 0x64, 0x5D, 0x75, 0x9A, 0x86, 0x2B, 0x2A, 0xC5, 0x2D, 0x3B, 0x01, 0x4A, 0x25, 0xE8, 0x47, 0x3F, 0x1F, 0x1E, 0xA4, 0xCF, 0xA8, 0x19, 0x93, 0x0A, 0xB3, + 0xA3, 0x4D, 0x71, 0x0D, 0xEE, 0xE7, 0x0C, 0xA1, 0x3E, 0x88, 0xFD, 0x71, 0xAA, 0x06, 0x4E, 0x6C, 0xB4, 0x69, 0x7D, 0xE0, 0xE4, 0x63, 0xB1, 0x37, 0x0A, 0x6A, 0x3B, 0xFE, 0x98, 0xFD, 0xFE, 0x7B, + 0x54, 0x71, 0xFF, 0x8D, 0xF6, 0xA6, 0x87, 0x9F, 0xBE, 0xF9, 0xAF, 0xB3, 0x51, 0x9D, 0x78, 0x07, 0x57, 0xD6, 0x74, 0x40, 0xAC, 0x36, 0xE8, 0x37, 0xBA, 0xC3, 0x83, 0x3E, 0xEA, 0xA9, 0x80, 0xBD, + 0x82, 0xB7, 0x93, 0x64, 0x36, 0xA0, 0x30, 0x7D, 0x16, 0x4B, 0x64, 0x38, 0x86, 0x9A, 0xE6, 0x06, 0xE9, 0x80, 0x51, 0x8E, 0x91, 0x3D, 0x0E, 0xE3, 0x02, 0x39, 0x6E, 0xF4, 0xEB, 0x25, 0xD9, 0x86, + 0x6E, 0x4B, 0xAF, 0xA1, 0x01, 0xE5, 0x99, 0x29, 0x31, 0x36, 0x1C, 0x4A, 0x98, 0x22, 0x53, 0xD5, 0x8A, 0xBE, 0x3B, 0xD5, 0x71, 0x07, 0x63, 0x5A, 0x46, 0xF0, 0x95, 0x12, 0x08, 0x5F, 0x4A, 0xDA, + 0x08, 0xEC, 0x8B, 0x1B, 0x39, 0x10, 0xB0, 0x15, 0x3B, 0x2A, 0xAF, 0xCA, 0xE5, 0x03, 0x3E, 0xDD, 0x41, 0x53, 0x24, 0x8D, 0xCD, 0x85, 0xB0, 0x2C, 0x9A, 0x25, 0xD8, 0xBD, 0xC4, 0x06, 0x8B, 0xB8, + 0x57, 0x41, 0x72, 0x62, 0x97, 0xA2, 0x5A, 0xEC, 0x55, 0xC4, 0x4A, 0xA2, 0x80, 0x59, 0xB7, 0x1B, 0xB9, 0xF3, 0x40, 0x67, 0x88, 0x7A, 0xDE, 0x4C, 0x1C, 0xA4, 0x90, 0x8B, 0x19, 0xB3, 0xD7, 0x81, + 0x23, 0x45, 0x38, 0x76, 0xDB, 0x4D, 0xCE, 0xB4, 0x27, 0x73, 0x06, 0x95, 0x72, 0xCD, 0x87, 0x77, 0xE6, 0x2C, 0xFB, 0xAF, 0x72, 0x03, 0xF0, 0x20, 0xF2, 0x81, 0xA6, 0x67, 0x8F, 0x79, 0x07, 0x20, + 0xEA, 0xA2, 0x0E, 0x34, 0x32, 0x7D, 0x7A, 0x63, 0x68, 0x8B, 0x09, 0xA0, 0x1F, 0x4D, 0x70, 0x88, 0xF7, 0xB5, 0x05, 0x9E, 0xDD, 0xEB, 0x45, 0xC0, 0xCE, 0x39, 0x32, 0x1C, 0x79, 0x52, 0x1D, 0x79, + 0xA5, 0x9E, 0xCD, 0xD4, 0x68, 0xCE, 0xD0, 0xEA, 0x82, 0xCA, 0x48, 0x49, 0x28, 0x70, 0x2F, 0x57, 0xD6, 0xFC, 0x18, 0xD3, 0x47, 0xAF, 0x3E, 0xD2, 0x2A, 0xAF, 0x45, 0xAB, 0xB0, 0xF2, 0x0B, 0xAB, + 0x9E, 0x01, 0x55, 0x76, 0x07, 0xAE, 0x3E, 0xD9, 0xCF, 0x0E, 0x26, 0xD3, 0x4D, 0x30, 0x54, 0x49, 0x66, 0x9E, 0xC6, 0xFC, 0x1B, 0xEC, 0xEA, 0xDC, 0xE1, 0x83, 0xF7, 0xA5, 0x94, 0xCE, 0xA1, 0x96, + 0xD0, 0x59, 0xA1, 0xE5, 0x50, 0xE5, 0x47, 0x86, 0x6C, 0xC0, 0x87, 0x33, 0x3F, 0x03, 0x0E, 0x62, 0x8F, 0x2C, 0xF1, 0x14, 0x79, 0x25, 0x41, 0x0E, 0xD0, 0x42, 0x1D, 0xC7, 0x50, 0x61, 0x38, 0xB1, + 0xD1, 0x90, 0x99, 0xC6, 0x95, 0xE1, 0xAF, 0xDA, 0xCE, 0x41, 0x53, 0x82, 0x5B, 0x66, 0xA8, 0xEC, 0xF5, 0x5A, 0x02, 0x1D, 0x21, 0xEB, 0x9F, 0x84, 0x8F, 0xE5, 0x5C, 0x21, 0x76, 0x9A, 0x75, 0x5F, + 0xA9, 0x80, 0x7E, 0xF7, 0x3A, 0x6C, 0x5B, 0xA1, 0x5A, 0x06, 0x34, 0x7D, 0x3F, 0x1C, 0x5C, 0x61, 0x9A, 0x31, 0x55, 0x98, 0x62, 0x91, 0x06, 0xAC, 0x0B, 0x86, 0xAE, 0x0D, 0x8E, 0x55, 0x57, 0x82, + 0x92, 0x51, 0x72, 0x58, 0xAE, 0x85, 0xF7, 0x2E, 0x73, 0x7A, 0xF5, 0x63, 0x8D, 0x09, 0x6B, 0x76, 0xA3, 0xC5, 0x7F, 0x1B, 0x9C, 0x80, 0xE7, 0x70, 0xA2, 0xD4, 0xEA, 0x4E, 0x42, 0xFE, 0x46, 0x9A, + 0xD4, 0x21, 0x28, 0x52, 0x41, 0x96, 0x0A, 0x8A, 0x86, 0x35, 0x5E, 0xF2, 0x2F, 0x58, 0x3F, 0xE3, 0xBA, 0xCA, 0xDF, 0x8D, 0xA3, 0x1D, 0x5C, 0x2D, 0xE2, 0x54, 0x16, 0x1B, 0xC6, 0xD1, 0x0F, 0x98, + 0x41, 0xDD, 0x27, 0xED, 0x46, 0x2A, 0x6B, 0x94, 0xB6, 0xDE, 0xEA, 0x90, 0xCB, 0xAB, 0x68, 0x7F, 0xB8, 0x4B, 0x56, 0x39, 0x5D, 0xA7, 0x63, 0xAB, 0x4B, 0x7F, 0xE3, 0x09, 0x5D, 0x57, 0x2D, 0x77, + 0xEF, 0xF3, 0xFF, 0x0D, 0x8F, 0x9D, 0x19, 0xAA, 0x5A, 0xF7, 0xB6, 0x76, 0x05, 0x3D, 0xBE, 0xF6, 0x4E, 0x61, 0xDD, 0x0A, 0x41, 0xD4, 0x02, 0x31, 0x8E, 0x33, 0x08, 0x66, 0x91, 0x06, 0x25, 0x9B, + 0xF7, 0xA4, 0xCE, 0x31, 0xB3, 0x46, 0xA9, 0xE9, 0x83, 0xED, 0xAB, 0xA0, 0x51, 0x80, 0x14, 0x9A, 0xB0, 0x57, 0xF9, 0x97, 0x29, 0x77, 0xDA, 0x7C, 0x6F, 0x46, 0xE0, 0xCD, 0xF8, 0x6F, 0x30, 0x91, + 0xF0, 0x4F, 0xD4, 0xE8, 0x3C, 0x60, 0x22, 0xE1, 0x8C, 0xE4, 0x38, 0x2B, 0x54, 0xD5, 0xDA, 0xBA, 0x82, 0xE4, 0xDF, 0x1E, 0x53, 0xBF, 0x31, 0xFE, 0x4B, 0xB6, 0x5A, 0x85, 0x24, 0xED, 0xA8, 0x3F, + 0xD2, 0x9D, 0x07, 0xE4, 0x97, 0x47, 0xB7, 0x52, 0x91, 0xCB, 0xC8, 0xF8, 0xEE, 0x14, 0x15, 0xEC, 0x92, 0x1E, 0x19, 0x02, 0x2A, 0xDE, 0x2C, 0x04, 0x7E, 0x4D, 0xF3, 0x50, 0x72, 0x89, 0xE9, 0xD7, + 0x9A, 0x8E, 0x69, 0x92, 0xB4, 0x8B, 0x88, 0x64, 0x20, 0x4A, 0x41, 0x6B, 0x76, 0x9C, 0xC7, 0x87, 0xD6, 0xDF, 0x44, 0x07, 0xE9, 0x3D, 0x12, 0x1F, 0x7F, 0xBE, 0xE0, 0xE4, 0x08, 0x96, 0x3E, 0x06, + 0x09, 0xA9, 0xC7, 0x5C, 0xB3, 0x11, 0x7C, 0xA5, 0x83, 0xDF, 0x6E, 0x79, 0xF3, 0x1C, 0x63, 0x5B, 0xF0, 0xF1, 0xBE, 0x98, 0xDF, 0x55, 0x07, 0x27, 0xA4, 0x5D, 0x3C, 0xA3, 0x37, 0xD7, 0x9D, 0xE5, + 0xDC, 0xDB, 0x0B, 0x91, 0xCA, 0xBB, 0xC3, 0x0D, 0x7E, 0xF0, 0xAE, 0x1C, 0xA1, 0xE9, 0x49, 0x04, 0xF7, 0x8C, 0x1F, 0xD8, 0xFB, 0xA8, 0x75, 0x45, 0xFD, 0xC1, 0x74, 0xAD, 0x81, 0x90, 0xF9, 0xB5, + 0xED, 0x7B, 0x58, 0x69, 0x49, 0x4F, 0xFA, 0x91, 0x03, 0x3F, 0xDC, 0x61, 0x17, 0xBF, 0x66, 0x2E, 0xC5, 0xF2, 0xAF, 0x26, 0x34, 0xBA, 0x3F, 0x8C, 0x02, 0x21, 0x0F, 0x1C, 0x9B, 0xCD, 0xDA, 0x9B, + 0xB3, 0x97, 0x60, 0xE0, 0x0F, 0x25, 0xA7, 0x27, 0x0C, 0x34, 0x56, 0x66, 0xFB, 0x6D, 0xF8, 0x5C, 0x91, 0x9A, 0xA1, 0x50, 0xCA, 0x7F, 0xC8, 0x0F, 0xC0, 0xEA, 0xCF, 0xE2, 0x42, 0xEF, 0x55, 0xF4, + 0x29, 0x80, 0x63, 0x62, 0x8E, 0x61, 0x05, 0x6C, 0x96, 0x6D, 0xB9, 0x96, 0x44, 0x28, 0xD9, 0xCE, 0x99, 0x10, 0x82, 0x71, 0xE2, 0x9A, 0x12, 0x32, 0x8E, 0x23, 0x99, 0x97, 0x34, 0xE0, 0x36, 0xF1, + 0x8A, 0x0E, 0xB8, 0xF0, 0x30, 0xE8, 0x80, 0x62, 0xC5, 0x67, 0x17, 0xE7, 0xA3, 0x63, 0x14, 0xE4, 0x4E, 0xCF, 0x35, 0x7F, 0xF5, 0x6E, 0xED, 0xF9, 0x0D, 0x3F, 0xB1, 0x1B, 0x22, 0xA1, 0xB2, 0x59, + 0x05, 0xB3, 0x79, 0xFC, 0xCA, 0x5C, 0xA1, 0xAC, 0xB9, 0x56, 0xE1, 0x78, 0xAD, 0x3F, 0x51, 0xD5, 0x35, 0xAD, 0x11, 0x98, 0x13, 0xB1, 0xE7, 0x0F, 0x73, 0x17, 0x65, 0x1B, 0xC7, 0x5C, 0xAC, 0x64, + 0x27, 0x6B, 0xB9, 0x81, 0x10, 0xB5, 0x4E, 0xA0, 0xEF, 0x34, 0x54, 0x1D, 0x73, 0x91, 0x07, 0x21, 0xD6, 0x57, 0x38, 0x76, 0x77, 0xE3, 0x32, 0xE9, 0xC8, 0x81, 0x1C, 0x3F, 0xC1, 0xB9, 0x23, 0xB2, + 0xEE, 0x9C, 0x51, 0x2F, 0x6D, 0x09, 0xDF, 0x37, 0x2A, 0x5F, 0x97, 0xFA, 0xD7, 0x12, 0x33, 0x89, 0xCE, 0xE1, 0x97, 0xB5, 0xC2, 0x69, 0xE2, 0x21, 0xD7, 0xEE, 0xD3, 0x16, 0x0A, 0x52, 0x1E, 0x56, + 0xFF, 0x8A, 0xAF, 0xAB, 0x68, 0x61, 0x79, 0xD0, 0x9D, 0x78, 0xFC, 0x38, 0x7B, 0x3E, 0xA6, 0xA6, 0x72, 0x03, 0x4D, 0x24, 0xAC, 0x79, 0x99, 0xD1, 0x96, 0xB2, 0x31, 0x64, 0x75, 0xF3, 0x7D, 0xB8, + 0xE9, 0xED, 0x43, 0x1D, 0xF5, 0x83, 0x41, 0xFA, 0x88, 0x00, 0x3D, 0x3C, 0x64, 0x89, 0xE7, 0x80, 0x53, 0xD8, 0xE4, 0x4C, 0xE7, 0xE1, 0x6A, 0xEF, 0x41, 0x68, 0x59, 0xB3, 0xD2, 0xAE, 0xCE, 0x09, + 0x08, 0x6A, 0x74, 0x8B, 0x7B, 0xCF, 0xD1, 0x0F, 0x73, 0xE3, 0xCF, 0x8B, 0x31, 0xF0, 0xCC, 0x44, 0xDA, 0x05, 0x9C, 0x69, 0xAB, 0xA5, 0xBC, 0x8E, 0xFA, 0xD4, 0x5D, 0x3F, 0x37, 0x6A, 0xF3, 0xA0, + 0xDE, 0x6E, 0x16, 0x98, 0x78, 0xBD, 0x84, 0x2E, 0x28, 0x79, 0x8E, 0x47, 0x43, 0xF8, 0x43, 0x84, 0x4B, 0xCD, 0xF8, 0x50, 0x6F, 0x13, 0x63, 0x91, 0xEC, 0x8E, 0x72, 0x1D, 0xC2, 0xB6, 0x28, 0x2D, + 0x9C, 0x50, 0xFA, 0xB6, 0x53, 0xA6, 0xAB, 0xF2, 0x89, 0x47, 0x42, 0x0E, 0x8C, 0x22, 0xA9, 0xA4, 0x87, 0xD7, 0x6A, 0x93, 0x89, 0x33, 0xB3, 0x4E, 0x49, 0x7D, 0xA9, 0x53, 0x94, 0x17, 0x6B, 0x27, + 0x74, 0xC0, 0x9E, 0xF0, 0xBB, 0x1E, 0xD8, 0xC3, 0xB1, 0x31, 0xA2, 0x19, 0x57, 0xB3, 0x1A, 0x0B, 0x47, 0xCB, 0xFB, 0xFF, 0x05, 0x33, 0xCA, 0xF3, 0x31, 0x25, 0x22, 0x1D, 0xB6, 0xBA, 0x4A, 0x51, + 0x88, 0x64, 0x89, 0x2C, 0xF2, 0x1D, 0x3D, 0x4D, 0x58, 0xB5, 0x99, 0xA3, 0x7A, 0x08, 0xF3, 0x44, 0xAA, 0x7E, 0xF9, 0x8E, 0x7D, 0x7D, 0x9D, 0x33, 0x16, 0xA6, 0xB1, 0x15, 0xD9, 0xB8, 0xF2, 0x0F, + 0x93, 0xBC, 0x68, 0x65, 0x73, 0x46, 0x99, 0xEB, 0x54, 0xC8, 0x88, 0xD7, 0xE5, 0xA0, 0xAC, 0xAF, 0xD1, 0x91, 0x53, 0x52, 0xB2, 0x94, 0x24, 0x37, 0x12, 0xCF, 0xE8, 0x2F, 0x85, 0x24, 0x8B, 0x00, + 0x04, 0x5C, 0xF3, 0xD0, 0x90, 0xC0, 0xC0, 0x0D, 0x7C, 0xA0, 0xE3, 0xA1, 0xF1, 0x47, 0x70, 0x3F, 0xD9, 0x4F, 0x71, 0x7E, 0x49, 0xC8, 0x1A, 0x7C, 0x3A, 0x76, 0x94, 0x6E, 0x20, 0xA6, 0x3F, 0x3B, + 0x7C, 0x3E, 0xAB, 0xA9, 0x22, 0x5A, 0xBE, 0x0B, 0x34, 0xCB, 0x0C, 0xF2, 0x35, 0x06, 0x39, 0x67, 0xD1, 0x6B, 0xC8, 0xA6, 0x9C, 0x13, 0x0C, 0xCE, 0x28, 0x76, 0x15, 0xCC, 0x05, 0x31, 0x14, 0x16, + 0x7E, 0xAC, 0x4E, 0x95, 0xBB, 0xAB, 0xDF, 0xBB, 0xCF, 0x96, 0xBC, 0x0C, 0x0D, 0x65, 0xEA, 0x00, 0x0A, 0xEA, 0xF4, 0x90, 0xD7, 0x23, 0x95, 0x5B, 0xD1, 0xB4, 0xD6, 0x91, 0x54, 0xD2, 0x62, 0xF6, + 0xA6, 0xD3, 0x53, 0x4B, 0xB0, 0xBC, 0x39, 0x7C, 0x29, 0xEC, 0xC6, 0xB1, 0x44, 0x7B, 0x75, 0xC9, 0x53, 0xAF, 0x44, 0x1D, 0xE2, 0xE7, 0x13, 0x3A, 0x7A, 0xC9, 0x89, 0x88, 0xA7, 0xEF, 0x9E, 0x6E, + 0xE6, 0x35, 0x58, 0xAA, 0xAD, 0xA0, 0x60, 0x3B, 0xD5, 0x29, 0x77, 0x6F, 0x05, 0x55, 0x8D, 0x2D, 0xF5, 0x64, 0x1C, 0x41, 0x2E, 0x73, 0x47, 0x44, 0x0F, 0x65, 0xEB, 0x82, 0x3A, 0xFC, 0x7C, 0xCA, + 0xE6, 0xB9, 0x71, 0x08, 0xB8, 0x57, 0x28, 0x7A, 0x04, 0x86, 0xDB, 0xBE, 0x68, 0x9D, 0x77, 0x0C, 0xA9, 0x24, 0x71, 0x30, 0x9E, 0x73, 0xAD, 0x39, 0x0A, 0xBF, 0x56, 0x91, 0x2B, 0x2B, 0x7C, 0x49, + 0x24, 0x2C, 0xEC, 0x15, 0x7B, 0xDB, 0xBD, 0x49, 0x35, 0x53, 0x73, 0x5C, 0xB1, 0xD9, 0xB4, 0x0A, 0xFC, 0x21, 0x4D, 0xA1, 0x53, 0x35, 0x9C, 0x9D, 0xF5, 0x76, 0x13, 0x59, 0x01, 0xC2, 0xFD, 0xA5, + 0x8C, 0x00, 0x95, 0xB6, 0xFC, 0xE3, 0xFD, 0x07, 0x31, 0xDF, 0x34, 0x86, 0x3A, 0xF2, 0x88, 0x2D, 0x53, 0x77, 0x3C, 0xE7, 0xC1, 0x82, 0x47, 0x37, 0x22, 0xAA, 0x79, 0xA6, 0xB3, 0x7D, 0x3E, 0xDD, + 0xDE, 0x38, 0xFA, 0x71, 0xDF, 0x8C, 0x0E, 0xDC, 0x08, 0x1E, 0xFE, 0xD8, 0xCE, 0x60, 0x6E, 0x48, 0x29, 0x91, 0x80, 0xEC, 0x6F, 0xE3, 0x5F, 0xAB, 0x64, 0x99, 0x10, 0xC4, 0x8A, 0x6A, 0x29, 0xF9, + 0xD0, 0xF8, 0x55, 0x57, 0xE1, 0x0B, 0xC5, 0xAE, 0x2E, 0xCF, 0x02, 0x8A, 0xE3, 0x99, 0xF5, 0x5C, 0xD7, 0x97, 0x60, 0x28, 0x93, 0x5C, 0xC0, 0x3C, 0x0C, 0xAF, 0xD5, 0x00, 0x3C, 0x9E, 0xAE, 0xD2, + 0x47, 0xFB, 0xE3, 0x0A, 0x28, 0x4C, 0xC4, 0x47, 0x0A, 0x55, 0x25, 0xA6, 0x49, 0x8E, 0x1D, 0xBB, 0xD3, 0x08, 0x5C, 0x3F, 0x9D, 0x77, 0xC6, 0x06, 0x4D, 0x01, 0x81, 0xBC, 0x5A, 0x82, 0x95, 0x61, + 0x56, 0x0A, 0xA9, 0xA4, 0xEA, 0x81, 0x73, 0xD7, 0x93, 0x7A, 0x94, 0x28, 0x10, 0x9C, 0xB3, 0xA6, 0x6B, 0x2B, 0x3D, 0xE1, 0x1F, 0x88, 0xF5, 0x5A, 0xB2, 0x1E, 0xB4, 0x9B, 0x77, 0xA3, 0x97, 0x62, + 0xCA, 0x92, 0x64, 0xE0, 0x15, 0x65, 0x66, 0x76, 0x5E, 0x2D, 0x36, 0x26, 0xB7, 0x2B, 0x80, 0xBD, 0x14, 0x11, 0xE4, 0xEC, 0x53, 0x55, 0x28, 0x28, 0xA2, 0x4B, 0xC8, 0xCD, 0xC4, 0x7F, 0x46, 0x5F, + 0xDD, 0xF4, 0x77, 0x2C, 0x7B, 0xC0, 0x20, 0x66, 0x85, 0x40, 0x11, 0x28, 0x7F, 0x73, 0x9A, 0xBA, 0x60, 0x47, 0x59, 0x67, 0x47, 0xF4, 0x23, 0x4A, 0xE2, 0x27, 0xDB, 0xFF, 0xAB, 0xF0, 0xE1, 0x31, + 0x53, 0xE2, 0xE0, 0x69, 0xF0, 0xB7, 0x90, 0x25, 0x1B, 0xE8, 0x77, 0xFE, 0x5A, 0x19, 0x8E, 0x80, 0x82, 0x58, 0x63, 0x9F, 0x5E, 0x79, 0xD3, 0xD5, 0xCD, 0x16, 0xF1, 0xA5, 0x73, 0x72, 0x4D, 0xD6, + 0xA9, 0xF6, 0x99, 0x0C, 0x45, 0x02, 0x33, 0x4D, 0xC6, 0x6F, 0x65, 0x49, 0x34, 0x90, 0x67, 0x3A, 0xB3, 0x0D, 0xCA, 0x7C, 0x03, 0x1F, 0x0C, 0x21, 0x2C, 0x0D, 0x8B, 0xC9, 0xD0, 0xC8, 0x74, 0xB3, + 0x19, 0xA9, 0x7A, 0xD1, 0xCE, 0x93, 0x95, 0xD3, 0xD1, 0x54, 0x20, 0x31, 0x56, 0xC5, 0x1C, 0xC3, 0xB9, 0xCB, 0x13, 0xD0, 0xBA, 0x1B, 0xDF, 0x61, 0x8B, 0xC8, 0xEE, 0xCA, 0x9D, 0xDD, 0x94, 0x12, + 0x05, 0x0C, 0xFA, 0x09, 0x23, 0x57, 0x27, 0xAA, 0x50, 0xD4, 0x6F, 0x79, 0xAD, 0x6F, 0x3C, 0x5A, 0x1B, 0xB6, 0xB2, 0x84, 0xC8, 0x31, 0x1D, 0xCF, 0x93, 0x75, 0x68, 0x59, 0x70, 0x4D, 0xF8, 0xFC, + 0x3B, 0xB8, 0xD2, 0xF5, 0xE0, 0x94, 0xE0, 0x45, 0x02, 0x35, 0x49, 0x42, 0xE9, 0xC8, 0x52, 0xB2, 0x08, 0xD4, 0x90, 0x18, 0x34, 0x33, 0x2E, 0xBC, 0x60, 0x32, 0x70, 0xCB, 0x57, 0xED, 0x41, 0x8C, + 0x34, 0xCE, 0x48, 0xAA, + }, + .spki_len = 2630, + .spki = { + 0x30, 0x82, 0x0A, 0x42, 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0B, 0x07, 0x08, 0x07, 0x05, 0x00, 0x03, 0x82, 0x0A, 0x2D, 0x00, 0x30, 0x82, 0x0A, 0x28, 0x03, 0x21, + 0x00, 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, 0x38, 0xD5, 0x06, 0xD8, 0x5B, + 0xEF, 0x03, 0x82, 0x0A, 0x01, 0x00, 0x03, 0x23, 0x69, 0xA2, 0xCE, 0x57, 0x2F, 0xD0, 0x8B, 0xFC, 0x30, 0x4B, 0x48, 0x48, 0xE7, 0x8D, 0x75, 0x2D, 0x77, 0xE9, 0x7A, 0x28, 0xB9, 0x9B, 0x9B, 0xB6, + 0xFB, 0x5C, 0x7C, 0x63, 0x37, 0x51, 0x4B, 0x32, 0x1E, 0xCD, 0xC1, 0xFB, 0x66, 0x9F, 0x26, 0xD4, 0x17, 0x1A, 0xB4, 0x2B, 0x72, 0x72, 0x0E, 0xE7, 0x0E, 0x05, 0x19, 0xA6, 0xE1, 0xD3, 0xD6, 0xD9, + 0x91, 0x4E, 0xC1, 0xB2, 0x1C, 0xDE, 0x38, 0xB4, 0x1A, 0xAC, 0x1D, 0x3A, 0xBE, 0xE6, 0xF2, 0xB7, 0x49, 0x5C, 0x4C, 0x82, 0x0C, 0x1F, 0xC0, 0xCC, 0x9E, 0x71, 0xE2, 0x4C, 0xFB, 0x5C, 0x9C, 0x0D, + 0x8E, 0xEF, 0x42, 0x64, 0xAF, 0x48, 0x4F, 0xAE, 0x4D, 0x6E, 0x5D, 0xDE, 0x65, 0xD4, 0xDF, 0x72, 0xB6, 0x1C, 0x6D, 0xBD, 0x26, 0xF8, 0x61, 0xA5, 0xE0, 0xB8, 0x53, 0xAC, 0x54, 0x13, 0x22, 0x6F, + 0xEB, 0xBA, 0xBA, 0x5E, 0xB4, 0x74, 0xC6, 0xFB, 0x25, 0xA8, 0x26, 0x78, 0xEA, 0x16, 0x06, 0xB4, 0x52, 0xA2, 0x31, 0x12, 0x22, 0x10, 0x17, 0xB8, 0xC0, 0x73, 0xC1, 0x03, 0x78, 0xF9, 0x14, 0x56, + 0x41, 0xA8, 0xC0, 0x78, 0xC0, 0xED, 0x9E, 0x42, 0x16, 0x50, 0xF7, 0x48, 0x89, 0x25, 0x22, 0xAB, 0x9F, 0xB7, 0xD1, 0xFF, 0x8C, 0xF1, 0xCC, 0x71, 0xB8, 0x56, 0x6E, 0x8D, 0xA3, 0x3C, 0xD7, 0x36, + 0x17, 0x70, 0xC0, 0x44, 0x34, 0x9A, 0xC4, 0x40, 0xCC, 0xCD, 0xC6, 0xBB, 0xE3, 0x5E, 0x6C, 0x55, 0x78, 0x27, 0x66, 0xF3, 0x8E, 0x68, 0x8B, 0xF4, 0x78, 0x21, 0x03, 0x72, 0x99, 0xE3, 0x44, 0xEC, + 0xDE, 0xCA, 0x17, 0xAD, 0x5D, 0x15, 0xCD, 0x27, 0xA4, 0xF7, 0xB0, 0x70, 0x66, 0x11, 0x38, 0xED, 0xE8, 0xED, 0x72, 0xA8, 0x95, 0x9C, 0x5A, 0xE3, 0x6B, 0x1C, 0x46, 0x09, 0x4A, 0x53, 0xCB, 0x21, + 0xA7, 0xA4, 0x26, 0x73, 0xF1, 0x40, 0x1C, 0x2B, 0x25, 0x94, 0x94, 0x09, 0x0E, 0x2F, 0x53, 0xD7, 0xEE, 0x70, 0x63, 0x43, 0x1E, 0xE5, 0x85, 0x80, 0x02, 0xD8, 0x50, 0xAF, 0x90, 0x9C, 0x37, 0x83, + 0x43, 0x60, 0x10, 0xF7, 0xEA, 0x88, 0x62, 0x5A, 0x36, 0xA0, 0xF0, 0x18, 0x9F, 0xDE, 0x75, 0xB7, 0xE8, 0xC7, 0xE4, 0xB1, 0x9D, 0x85, 0x27, 0x00, 0x83, 0x28, 0xAD, 0xBC, 0x92, 0x9B, 0xBC, 0x86, + 0xE9, 0x64, 0xCF, 0xC4, 0x8B, 0x8C, 0xF1, 0xDA, 0x5D, 0x7E, 0xD3, 0x33, 0x3A, 0xB5, 0x5C, 0x15, 0x07, 0x28, 0x32, 0x21, 0x4A, 0x77, 0x9A, 0x5F, 0xD1, 0x0C, 0xC0, 0x40, 0x05, 0xF4, 0x6C, 0x1A, + 0xA8, 0x88, 0x4A, 0x16, 0x19, 0x92, 0x47, 0x2F, 0xD5, 0x35, 0xB9, 0x5E, 0xD1, 0x8B, 0xDE, 0x1C, 0x6D, 0x8C, 0xE6, 0x78, 0xD2, 0x81, 0x7D, 0x69, 0xF9, 0x05, 0x71, 0x10, 0x3E, 0x85, 0x20, 0xE7, + 0x31, 0x3C, 0xE7, 0xB9, 0x30, 0xC5, 0xEB, 0xFA, 0xF2, 0xF4, 0xEC, 0x75, 0x8B, 0x62, 0x6B, 0x55, 0x43, 0xA0, 0x68, 0xCD, 0xE0, 0xFD, 0x0E, 0x94, 0xE6, 0xA6, 0x44, 0x75, 0xB2, 0x32, 0x68, 0xBF, + 0x03, 0x80, 0xD0, 0x75, 0x50, 0x8F, 0x85, 0x12, 0x8C, 0xA2, 0x6F, 0x31, 0xA9, 0x0C, 0x4A, 0x7D, 0x28, 0x44, 0x0D, 0x54, 0xD4, 0x06, 0x6B, 0x40, 0x45, 0x88, 0x58, 0x8B, 0x4C, 0xCF, 0x85, 0x0B, + 0x97, 0x5C, 0x73, 0xAF, 0xE6, 0x8C, 0xBC, 0xD1, 0x02, 0x75, 0x5F, 0x61, 0xEB, 0x3E, 0x60, 0x32, 0x3C, 0x57, 0x6E, 0x52, 0x9E, 0xC0, 0xBF, 0x23, 0xBF, 0xA5, 0xBE, 0xA3, 0x9C, 0xB7, 0x3C, 0x37, + 0xE8, 0x39, 0x5D, 0x8D, 0xBD, 0x4C, 0x8D, 0xC8, 0xAB, 0x2F, 0x70, 0xA0, 0xBF, 0xC3, 0xA7, 0x8C, 0x0D, 0x41, 0x3F, 0x08, 0xD1, 0x4D, 0x63, 0x2B, 0xC0, 0x40, 0x3B, 0x03, 0x83, 0xDB, 0xBB, 0x22, + 0xBD, 0x9B, 0x11, 0x3C, 0x89, 0x45, 0x2A, 0xEA, 0xB1, 0x12, 0x10, 0x09, 0x79, 0x47, 0xFE, 0xAA, 0xA3, 0xC9, 0xF0, 0x5D, 0x1D, 0x30, 0x0C, 0x33, 0xA5, 0x5E, 0x3F, 0xBC, 0x81, 0x25, 0x9E, 0x86, + 0x27, 0x05, 0xC3, 0xA1, 0x3B, 0x9E, 0xE3, 0x5F, 0x6B, 0x23, 0xED, 0x10, 0xF4, 0xED, 0xEA, 0x95, 0x19, 0xFA, 0x91, 0xB7, 0xBC, 0xD0, 0xD5, 0x01, 0xB5, 0xED, 0x57, 0xD9, 0x04, 0x9F, 0xAB, 0x91, + 0xAA, 0x77, 0x9C, 0x72, 0x5F, 0xF8, 0xE9, 0xF7, 0x80, 0x17, 0xEA, 0x78, 0x07, 0xFA, 0x25, 0x4B, 0x71, 0x05, 0xE8, 0x26, 0xD0, 0x96, 0xC0, 0x1A, 0xDA, 0xE2, 0xC5, 0xD1, 0x38, 0x25, 0x1A, 0x92, + 0xA4, 0x78, 0xA3, 0x33, 0x73, 0xF4, 0xDE, 0x91, 0x2B, 0x83, 0xB6, 0xFB, 0x4B, 0x0D, 0x0D, 0xE6, 0xBC, 0x11, 0x18, 0xBB, 0x2F, 0xCF, 0xB0, 0x7B, 0xD2, 0x27, 0xA5, 0xF7, 0xF9, 0x91, 0x43, 0x9A, + 0x13, 0xDE, 0x12, 0x38, 0x18, 0x0C, 0xDC, 0x55, 0x11, 0x9E, 0x65, 0xC4, 0x18, 0x58, 0x4D, 0x80, 0x7A, 0x92, 0x6E, 0x4A, 0x9C, 0x0F, 0x70, 0x15, 0x5E, 0xE1, 0x96, 0xFB, 0x07, 0x65, 0x6D, 0x9A, + 0xA7, 0x98, 0x2B, 0x87, 0x95, 0xDB, 0xAD, 0x43, 0xD1, 0x05, 0x9C, 0xA7, 0xF5, 0x80, 0xD3, 0x32, 0x0C, 0x04, 0x38, 0xA5, 0xED, 0x5A, 0x70, 0x32, 0xB2, 0xE9, 0x59, 0x67, 0x84, 0x10, 0xF1, 0x1A, + 0xD9, 0x8B, 0xE8, 0x82, 0x6A, 0x44, 0x26, 0x26, 0x15, 0x64, 0x5D, 0x75, 0x9A, 0x86, 0x2B, 0x2A, 0xC5, 0x2D, 0x3B, 0x01, 0x4A, 0x25, 0xE8, 0x47, 0x3F, 0x1F, 0x1E, 0xA4, 0xCF, 0xA8, 0x19, 0x93, + 0x0A, 0xB3, 0xA3, 0x4D, 0x71, 0x0D, 0xEE, 0xE7, 0x0C, 0xA1, 0x3E, 0x88, 0xFD, 0x71, 0xAA, 0x06, 0x4E, 0x6C, 0xB4, 0x69, 0x7D, 0xE0, 0xE4, 0x63, 0xB1, 0x37, 0x0A, 0x6A, 0x3B, 0xFE, 0x98, 0xFD, + 0xFE, 0x7B, 0x54, 0x71, 0xFF, 0x8D, 0xF6, 0xA6, 0x87, 0x9F, 0xBE, 0xF9, 0xAF, 0xB3, 0x51, 0x9D, 0x78, 0x07, 0x57, 0xD6, 0x74, 0x40, 0xAC, 0x36, 0xE8, 0x37, 0xBA, 0xC3, 0x83, 0x3E, 0xEA, 0xA9, + 0x80, 0xBD, 0x82, 0xB7, 0x93, 0x64, 0x36, 0xA0, 0x30, 0x7D, 0x16, 0x4B, 0x64, 0x38, 0x86, 0x9A, 0xE6, 0x06, 0xE9, 0x80, 0x51, 0x8E, 0x91, 0x3D, 0x0E, 0xE3, 0x02, 0x39, 0x6E, 0xF4, 0xEB, 0x25, + 0xD9, 0x86, 0x6E, 0x4B, 0xAF, 0xA1, 0x01, 0xE5, 0x99, 0x29, 0x31, 0x36, 0x1C, 0x4A, 0x98, 0x22, 0x53, 0xD5, 0x8A, 0xBE, 0x3B, 0xD5, 0x71, 0x07, 0x63, 0x5A, 0x46, 0xF0, 0x95, 0x12, 0x08, 0x5F, + 0x4A, 0xDA, 0x08, 0xEC, 0x8B, 0x1B, 0x39, 0x10, 0xB0, 0x15, 0x3B, 0x2A, 0xAF, 0xCA, 0xE5, 0x03, 0x3E, 0xDD, 0x41, 0x53, 0x24, 0x8D, 0xCD, 0x85, 0xB0, 0x2C, 0x9A, 0x25, 0xD8, 0xBD, 0xC4, 0x06, + 0x8B, 0xB8, 0x57, 0x41, 0x72, 0x62, 0x97, 0xA2, 0x5A, 0xEC, 0x55, 0xC4, 0x4A, 0xA2, 0x80, 0x59, 0xB7, 0x1B, 0xB9, 0xF3, 0x40, 0x67, 0x88, 0x7A, 0xDE, 0x4C, 0x1C, 0xA4, 0x90, 0x8B, 0x19, 0xB3, + 0xD7, 0x81, 0x23, 0x45, 0x38, 0x76, 0xDB, 0x4D, 0xCE, 0xB4, 0x27, 0x73, 0x06, 0x95, 0x72, 0xCD, 0x87, 0x77, 0xE6, 0x2C, 0xFB, 0xAF, 0x72, 0x03, 0xF0, 0x20, 0xF2, 0x81, 0xA6, 0x67, 0x8F, 0x79, + 0x07, 0x20, 0xEA, 0xA2, 0x0E, 0x34, 0x32, 0x7D, 0x7A, 0x63, 0x68, 0x8B, 0x09, 0xA0, 0x1F, 0x4D, 0x70, 0x88, 0xF7, 0xB5, 0x05, 0x9E, 0xDD, 0xEB, 0x45, 0xC0, 0xCE, 0x39, 0x32, 0x1C, 0x79, 0x52, + 0x1D, 0x79, 0xA5, 0x9E, 0xCD, 0xD4, 0x68, 0xCE, 0xD0, 0xEA, 0x82, 0xCA, 0x48, 0x49, 0x28, 0x70, 0x2F, 0x57, 0xD6, 0xFC, 0x18, 0xD3, 0x47, 0xAF, 0x3E, 0xD2, 0x2A, 0xAF, 0x45, 0xAB, 0xB0, 0xF2, + 0x0B, 0xAB, 0x9E, 0x01, 0x55, 0x76, 0x07, 0xAE, 0x3E, 0xD9, 0xCF, 0x0E, 0x26, 0xD3, 0x4D, 0x30, 0x54, 0x49, 0x66, 0x9E, 0xC6, 0xFC, 0x1B, 0xEC, 0xEA, 0xDC, 0xE1, 0x83, 0xF7, 0xA5, 0x94, 0xCE, + 0xA1, 0x96, 0xD0, 0x59, 0xA1, 0xE5, 0x50, 0xE5, 0x47, 0x86, 0x6C, 0xC0, 0x87, 0x33, 0x3F, 0x03, 0x0E, 0x62, 0x8F, 0x2C, 0xF1, 0x14, 0x79, 0x25, 0x41, 0x0E, 0xD0, 0x42, 0x1D, 0xC7, 0x50, 0x61, + 0x38, 0xB1, 0xD1, 0x90, 0x99, 0xC6, 0x95, 0xE1, 0xAF, 0xDA, 0xCE, 0x41, 0x53, 0x82, 0x5B, 0x66, 0xA8, 0xEC, 0xF5, 0x5A, 0x02, 0x1D, 0x21, 0xEB, 0x9F, 0x84, 0x8F, 0xE5, 0x5C, 0x21, 0x76, 0x9A, + 0x75, 0x5F, 0xA9, 0x80, 0x7E, 0xF7, 0x3A, 0x6C, 0x5B, 0xA1, 0x5A, 0x06, 0x34, 0x7D, 0x3F, 0x1C, 0x5C, 0x61, 0x9A, 0x31, 0x55, 0x98, 0x62, 0x91, 0x06, 0xAC, 0x0B, 0x86, 0xAE, 0x0D, 0x8E, 0x55, + 0x57, 0x82, 0x92, 0x51, 0x72, 0x58, 0xAE, 0x85, 0xF7, 0x2E, 0x73, 0x7A, 0xF5, 0x63, 0x8D, 0x09, 0x6B, 0x76, 0xA3, 0xC5, 0x7F, 0x1B, 0x9C, 0x80, 0xE7, 0x70, 0xA2, 0xD4, 0xEA, 0x4E, 0x42, 0xFE, + 0x46, 0x9A, 0xD4, 0x21, 0x28, 0x52, 0x41, 0x96, 0x0A, 0x8A, 0x86, 0x35, 0x5E, 0xF2, 0x2F, 0x58, 0x3F, 0xE3, 0xBA, 0xCA, 0xDF, 0x8D, 0xA3, 0x1D, 0x5C, 0x2D, 0xE2, 0x54, 0x16, 0x1B, 0xC6, 0xD1, + 0x0F, 0x98, 0x41, 0xDD, 0x27, 0xED, 0x46, 0x2A, 0x6B, 0x94, 0xB6, 0xDE, 0xEA, 0x90, 0xCB, 0xAB, 0x68, 0x7F, 0xB8, 0x4B, 0x56, 0x39, 0x5D, 0xA7, 0x63, 0xAB, 0x4B, 0x7F, 0xE3, 0x09, 0x5D, 0x57, + 0x2D, 0x77, 0xEF, 0xF3, 0xFF, 0x0D, 0x8F, 0x9D, 0x19, 0xAA, 0x5A, 0xF7, 0xB6, 0x76, 0x05, 0x3D, 0xBE, 0xF6, 0x4E, 0x61, 0xDD, 0x0A, 0x41, 0xD4, 0x02, 0x31, 0x8E, 0x33, 0x08, 0x66, 0x91, 0x06, + 0x25, 0x9B, 0xF7, 0xA4, 0xCE, 0x31, 0xB3, 0x46, 0xA9, 0xE9, 0x83, 0xED, 0xAB, 0xA0, 0x51, 0x80, 0x14, 0x9A, 0xB0, 0x57, 0xF9, 0x97, 0x29, 0x77, 0xDA, 0x7C, 0x6F, 0x46, 0xE0, 0xCD, 0xF8, 0x6F, + 0x30, 0x91, 0xF0, 0x4F, 0xD4, 0xE8, 0x3C, 0x60, 0x22, 0xE1, 0x8C, 0xE4, 0x38, 0x2B, 0x54, 0xD5, 0xDA, 0xBA, 0x82, 0xE4, 0xDF, 0x1E, 0x53, 0xBF, 0x31, 0xFE, 0x4B, 0xB6, 0x5A, 0x85, 0x24, 0xED, + 0xA8, 0x3F, 0xD2, 0x9D, 0x07, 0xE4, 0x97, 0x47, 0xB7, 0x52, 0x91, 0xCB, 0xC8, 0xF8, 0xEE, 0x14, 0x15, 0xEC, 0x92, 0x1E, 0x19, 0x02, 0x2A, 0xDE, 0x2C, 0x04, 0x7E, 0x4D, 0xF3, 0x50, 0x72, 0x89, + 0xE9, 0xD7, 0x9A, 0x8E, 0x69, 0x92, 0xB4, 0x8B, 0x88, 0x64, 0x20, 0x4A, 0x41, 0x6B, 0x76, 0x9C, 0xC7, 0x87, 0xD6, 0xDF, 0x44, 0x07, 0xE9, 0x3D, 0x12, 0x1F, 0x7F, 0xBE, 0xE0, 0xE4, 0x08, 0x96, + 0x3E, 0x06, 0x09, 0xA9, 0xC7, 0x5C, 0xB3, 0x11, 0x7C, 0xA5, 0x83, 0xDF, 0x6E, 0x79, 0xF3, 0x1C, 0x63, 0x5B, 0xF0, 0xF1, 0xBE, 0x98, 0xDF, 0x55, 0x07, 0x27, 0xA4, 0x5D, 0x3C, 0xA3, 0x37, 0xD7, + 0x9D, 0xE5, 0xDC, 0xDB, 0x0B, 0x91, 0xCA, 0xBB, 0xC3, 0x0D, 0x7E, 0xF0, 0xAE, 0x1C, 0xA1, 0xE9, 0x49, 0x04, 0xF7, 0x8C, 0x1F, 0xD8, 0xFB, 0xA8, 0x75, 0x45, 0xFD, 0xC1, 0x74, 0xAD, 0x81, 0x90, + 0xF9, 0xB5, 0xED, 0x7B, 0x58, 0x69, 0x49, 0x4F, 0xFA, 0x91, 0x03, 0x3F, 0xDC, 0x61, 0x17, 0xBF, 0x66, 0x2E, 0xC5, 0xF2, 0xAF, 0x26, 0x34, 0xBA, 0x3F, 0x8C, 0x02, 0x21, 0x0F, 0x1C, 0x9B, 0xCD, + 0xDA, 0x9B, 0xB3, 0x97, 0x60, 0xE0, 0x0F, 0x25, 0xA7, 0x27, 0x0C, 0x34, 0x56, 0x66, 0xFB, 0x6D, 0xF8, 0x5C, 0x91, 0x9A, 0xA1, 0x50, 0xCA, 0x7F, 0xC8, 0x0F, 0xC0, 0xEA, 0xCF, 0xE2, 0x42, 0xEF, + 0x55, 0xF4, 0x29, 0x80, 0x63, 0x62, 0x8E, 0x61, 0x05, 0x6C, 0x96, 0x6D, 0xB9, 0x96, 0x44, 0x28, 0xD9, 0xCE, 0x99, 0x10, 0x82, 0x71, 0xE2, 0x9A, 0x12, 0x32, 0x8E, 0x23, 0x99, 0x97, 0x34, 0xE0, + 0x36, 0xF1, 0x8A, 0x0E, 0xB8, 0xF0, 0x30, 0xE8, 0x80, 0x62, 0xC5, 0x67, 0x17, 0xE7, 0xA3, 0x63, 0x14, 0xE4, 0x4E, 0xCF, 0x35, 0x7F, 0xF5, 0x6E, 0xED, 0xF9, 0x0D, 0x3F, 0xB1, 0x1B, 0x22, 0xA1, + 0xB2, 0x59, 0x05, 0xB3, 0x79, 0xFC, 0xCA, 0x5C, 0xA1, 0xAC, 0xB9, 0x56, 0xE1, 0x78, 0xAD, 0x3F, 0x51, 0xD5, 0x35, 0xAD, 0x11, 0x98, 0x13, 0xB1, 0xE7, 0x0F, 0x73, 0x17, 0x65, 0x1B, 0xC7, 0x5C, + 0xAC, 0x64, 0x27, 0x6B, 0xB9, 0x81, 0x10, 0xB5, 0x4E, 0xA0, 0xEF, 0x34, 0x54, 0x1D, 0x73, 0x91, 0x07, 0x21, 0xD6, 0x57, 0x38, 0x76, 0x77, 0xE3, 0x32, 0xE9, 0xC8, 0x81, 0x1C, 0x3F, 0xC1, 0xB9, + 0x23, 0xB2, 0xEE, 0x9C, 0x51, 0x2F, 0x6D, 0x09, 0xDF, 0x37, 0x2A, 0x5F, 0x97, 0xFA, 0xD7, 0x12, 0x33, 0x89, 0xCE, 0xE1, 0x97, 0xB5, 0xC2, 0x69, 0xE2, 0x21, 0xD7, 0xEE, 0xD3, 0x16, 0x0A, 0x52, + 0x1E, 0x56, 0xFF, 0x8A, 0xAF, 0xAB, 0x68, 0x61, 0x79, 0xD0, 0x9D, 0x78, 0xFC, 0x38, 0x7B, 0x3E, 0xA6, 0xA6, 0x72, 0x03, 0x4D, 0x24, 0xAC, 0x79, 0x99, 0xD1, 0x96, 0xB2, 0x31, 0x64, 0x75, 0xF3, + 0x7D, 0xB8, 0xE9, 0xED, 0x43, 0x1D, 0xF5, 0x83, 0x41, 0xFA, 0x88, 0x00, 0x3D, 0x3C, 0x64, 0x89, 0xE7, 0x80, 0x53, 0xD8, 0xE4, 0x4C, 0xE7, 0xE1, 0x6A, 0xEF, 0x41, 0x68, 0x59, 0xB3, 0xD2, 0xAE, + 0xCE, 0x09, 0x08, 0x6A, 0x74, 0x8B, 0x7B, 0xCF, 0xD1, 0x0F, 0x73, 0xE3, 0xCF, 0x8B, 0x31, 0xF0, 0xCC, 0x44, 0xDA, 0x05, 0x9C, 0x69, 0xAB, 0xA5, 0xBC, 0x8E, 0xFA, 0xD4, 0x5D, 0x3F, 0x37, 0x6A, + 0xF3, 0xA0, 0xDE, 0x6E, 0x16, 0x98, 0x78, 0xBD, 0x84, 0x2E, 0x28, 0x79, 0x8E, 0x47, 0x43, 0xF8, 0x43, 0x84, 0x4B, 0xCD, 0xF8, 0x50, 0x6F, 0x13, 0x63, 0x91, 0xEC, 0x8E, 0x72, 0x1D, 0xC2, 0xB6, + 0x28, 0x2D, 0x9C, 0x50, 0xFA, 0xB6, 0x53, 0xA6, 0xAB, 0xF2, 0x89, 0x47, 0x42, 0x0E, 0x8C, 0x22, 0xA9, 0xA4, 0x87, 0xD7, 0x6A, 0x93, 0x89, 0x33, 0xB3, 0x4E, 0x49, 0x7D, 0xA9, 0x53, 0x94, 0x17, + 0x6B, 0x27, 0x74, 0xC0, 0x9E, 0xF0, 0xBB, 0x1E, 0xD8, 0xC3, 0xB1, 0x31, 0xA2, 0x19, 0x57, 0xB3, 0x1A, 0x0B, 0x47, 0xCB, 0xFB, 0xFF, 0x05, 0x33, 0xCA, 0xF3, 0x31, 0x25, 0x22, 0x1D, 0xB6, 0xBA, + 0x4A, 0x51, 0x88, 0x64, 0x89, 0x2C, 0xF2, 0x1D, 0x3D, 0x4D, 0x58, 0xB5, 0x99, 0xA3, 0x7A, 0x08, 0xF3, 0x44, 0xAA, 0x7E, 0xF9, 0x8E, 0x7D, 0x7D, 0x9D, 0x33, 0x16, 0xA6, 0xB1, 0x15, 0xD9, 0xB8, + 0xF2, 0x0F, 0x93, 0xBC, 0x68, 0x65, 0x73, 0x46, 0x99, 0xEB, 0x54, 0xC8, 0x88, 0xD7, 0xE5, 0xA0, 0xAC, 0xAF, 0xD1, 0x91, 0x53, 0x52, 0xB2, 0x94, 0x24, 0x37, 0x12, 0xCF, 0xE8, 0x2F, 0x85, 0x24, + 0x8B, 0x00, 0x04, 0x5C, 0xF3, 0xD0, 0x90, 0xC0, 0xC0, 0x0D, 0x7C, 0xA0, 0xE3, 0xA1, 0xF1, 0x47, 0x70, 0x3F, 0xD9, 0x4F, 0x71, 0x7E, 0x49, 0xC8, 0x1A, 0x7C, 0x3A, 0x76, 0x94, 0x6E, 0x20, 0xA6, + 0x3F, 0x3B, 0x7C, 0x3E, 0xAB, 0xA9, 0x22, 0x5A, 0xBE, 0x0B, 0x34, 0xCB, 0x0C, 0xF2, 0x35, 0x06, 0x39, 0x67, 0xD1, 0x6B, 0xC8, 0xA6, 0x9C, 0x13, 0x0C, 0xCE, 0x28, 0x76, 0x15, 0xCC, 0x05, 0x31, + 0x14, 0x16, 0x7E, 0xAC, 0x4E, 0x95, 0xBB, 0xAB, 0xDF, 0xBB, 0xCF, 0x96, 0xBC, 0x0C, 0x0D, 0x65, 0xEA, 0x00, 0x0A, 0xEA, 0xF4, 0x90, 0xD7, 0x23, 0x95, 0x5B, 0xD1, 0xB4, 0xD6, 0x91, 0x54, 0xD2, + 0x62, 0xF6, 0xA6, 0xD3, 0x53, 0x4B, 0xB0, 0xBC, 0x39, 0x7C, 0x29, 0xEC, 0xC6, 0xB1, 0x44, 0x7B, 0x75, 0xC9, 0x53, 0xAF, 0x44, 0x1D, 0xE2, 0xE7, 0x13, 0x3A, 0x7A, 0xC9, 0x89, 0x88, 0xA7, 0xEF, + 0x9E, 0x6E, 0xE6, 0x35, 0x58, 0xAA, 0xAD, 0xA0, 0x60, 0x3B, 0xD5, 0x29, 0x77, 0x6F, 0x05, 0x55, 0x8D, 0x2D, 0xF5, 0x64, 0x1C, 0x41, 0x2E, 0x73, 0x47, 0x44, 0x0F, 0x65, 0xEB, 0x82, 0x3A, 0xFC, + 0x7C, 0xCA, 0xE6, 0xB9, 0x71, 0x08, 0xB8, 0x57, 0x28, 0x7A, 0x04, 0x86, 0xDB, 0xBE, 0x68, 0x9D, 0x77, 0x0C, 0xA9, 0x24, 0x71, 0x30, 0x9E, 0x73, 0xAD, 0x39, 0x0A, 0xBF, 0x56, 0x91, 0x2B, 0x2B, + 0x7C, 0x49, 0x24, 0x2C, 0xEC, 0x15, 0x7B, 0xDB, 0xBD, 0x49, 0x35, 0x53, 0x73, 0x5C, 0xB1, 0xD9, 0xB4, 0x0A, 0xFC, 0x21, 0x4D, 0xA1, 0x53, 0x35, 0x9C, 0x9D, 0xF5, 0x76, 0x13, 0x59, 0x01, 0xC2, + 0xFD, 0xA5, 0x8C, 0x00, 0x95, 0xB6, 0xFC, 0xE3, 0xFD, 0x07, 0x31, 0xDF, 0x34, 0x86, 0x3A, 0xF2, 0x88, 0x2D, 0x53, 0x77, 0x3C, 0xE7, 0xC1, 0x82, 0x47, 0x37, 0x22, 0xAA, 0x79, 0xA6, 0xB3, 0x7D, + 0x3E, 0xDD, 0xDE, 0x38, 0xFA, 0x71, 0xDF, 0x8C, 0x0E, 0xDC, 0x08, 0x1E, 0xFE, 0xD8, 0xCE, 0x60, 0x6E, 0x48, 0x29, 0x91, 0x80, 0xEC, 0x6F, 0xE3, 0x5F, 0xAB, 0x64, 0x99, 0x10, 0xC4, 0x8A, 0x6A, + 0x29, 0xF9, 0xD0, 0xF8, 0x55, 0x57, 0xE1, 0x0B, 0xC5, 0xAE, 0x2E, 0xCF, 0x02, 0x8A, 0xE3, 0x99, 0xF5, 0x5C, 0xD7, 0x97, 0x60, 0x28, 0x93, 0x5C, 0xC0, 0x3C, 0x0C, 0xAF, 0xD5, 0x00, 0x3C, 0x9E, + 0xAE, 0xD2, 0x47, 0xFB, 0xE3, 0x0A, 0x28, 0x4C, 0xC4, 0x47, 0x0A, 0x55, 0x25, 0xA6, 0x49, 0x8E, 0x1D, 0xBB, 0xD3, 0x08, 0x5C, 0x3F, 0x9D, 0x77, 0xC6, 0x06, 0x4D, 0x01, 0x81, 0xBC, 0x5A, 0x82, + 0x95, 0x61, 0x56, 0x0A, 0xA9, 0xA4, 0xEA, 0x81, 0x73, 0xD7, 0x93, 0x7A, 0x94, 0x28, 0x10, 0x9C, 0xB3, 0xA6, 0x6B, 0x2B, 0x3D, 0xE1, 0x1F, 0x88, 0xF5, 0x5A, 0xB2, 0x1E, 0xB4, 0x9B, 0x77, 0xA3, + 0x97, 0x62, 0xCA, 0x92, 0x64, 0xE0, 0x15, 0x65, 0x66, 0x76, 0x5E, 0x2D, 0x36, 0x26, 0xB7, 0x2B, 0x80, 0xBD, 0x14, 0x11, 0xE4, 0xEC, 0x53, 0x55, 0x28, 0x28, 0xA2, 0x4B, 0xC8, 0xCD, 0xC4, 0x7F, + 0x46, 0x5F, 0xDD, 0xF4, 0x77, 0x2C, 0x7B, 0xC0, 0x20, 0x66, 0x85, 0x40, 0x11, 0x28, 0x7F, 0x73, 0x9A, 0xBA, 0x60, 0x47, 0x59, 0x67, 0x47, 0xF4, 0x23, 0x4A, 0xE2, 0x27, 0xDB, 0xFF, 0xAB, 0xF0, + 0xE1, 0x31, 0x53, 0xE2, 0xE0, 0x69, 0xF0, 0xB7, 0x90, 0x25, 0x1B, 0xE8, 0x77, 0xFE, 0x5A, 0x19, 0x8E, 0x80, 0x82, 0x58, 0x63, 0x9F, 0x5E, 0x79, 0xD3, 0xD5, 0xCD, 0x16, 0xF1, 0xA5, 0x73, 0x72, + 0x4D, 0xD6, 0xA9, 0xF6, 0x99, 0x0C, 0x45, 0x02, 0x33, 0x4D, 0xC6, 0x6F, 0x65, 0x49, 0x34, 0x90, 0x67, 0x3A, 0xB3, 0x0D, 0xCA, 0x7C, 0x03, 0x1F, 0x0C, 0x21, 0x2C, 0x0D, 0x8B, 0xC9, 0xD0, 0xC8, + 0x74, 0xB3, 0x19, 0xA9, 0x7A, 0xD1, 0xCE, 0x93, 0x95, 0xD3, 0xD1, 0x54, 0x20, 0x31, 0x56, 0xC5, 0x1C, 0xC3, 0xB9, 0xCB, 0x13, 0xD0, 0xBA, 0x1B, 0xDF, 0x61, 0x8B, 0xC8, 0xEE, 0xCA, 0x9D, 0xDD, + 0x94, 0x12, 0x05, 0x0C, 0xFA, 0x09, 0x23, 0x57, 0x27, 0xAA, 0x50, 0xD4, 0x6F, 0x79, 0xAD, 0x6F, 0x3C, 0x5A, 0x1B, 0xB6, 0xB2, 0x84, 0xC8, 0x31, 0x1D, 0xCF, 0x93, 0x75, 0x68, 0x59, 0x70, 0x4D, + 0xF8, 0xFC, 0x3B, 0xB8, 0xD2, 0xF5, 0xE0, 0x94, 0xE0, 0x45, 0x02, 0x35, 0x49, 0x42, 0xE9, 0xC8, 0x52, 0xB2, 0x08, 0xD4, 0x90, 0x18, 0x34, 0x33, 0x2E, 0xBC, 0x60, 0x32, 0x70, 0xCB, 0x57, 0xED, + 0x41, 0x8C, 0x34, 0xCE, 0x48, 0xAA, + }, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 4595, + .sig = { + 0xBB, 0xF8, 0x5F, 0xFD, 0x0E, 0x01, 0xC8, 0x0C, 0x8C, 0x1C, 0x19, 0x31, 0xCD, 0x64, 0x0B, 0xF2, 0x73, 0xD4, 0x96, 0x93, 0xC4, 0xC4, 0xBF, 0xF5, 0xDD, 0x20, 0xD9, 0x4C, 0xF3, 0x75, 0x7A, 0xBD, + 0x45, 0x47, 0x3B, 0x9D, 0x01, 0xB1, 0x87, 0x13, 0x05, 0xDA, 0x90, 0xED, 0xC6, 0x70, 0x7D, 0x54, 0x17, 0x12, 0x94, 0x67, 0xF6, 0x1F, 0x72, 0x39, 0x50, 0xC1, 0xAE, 0xDF, 0x70, 0x55, 0xEC, 0x1D, + 0x47, 0x77, 0xAD, 0x88, 0x08, 0xE8, 0xB3, 0x47, 0xD1, 0xD0, 0x92, 0x1E, 0xBA, 0xB8, 0x90, 0xCC, 0xA8, 0xE3, 0xA0, 0xDF, 0xD3, 0x00, 0x3D, 0xE9, 0xF9, 0xCB, 0x4A, 0x97, 0xD8, 0x84, 0xE1, 0xDD, + 0x04, 0x2C, 0x95, 0x8B, 0x81, 0x6F, 0x72, 0x37, 0x03, 0x2B, 0x20, 0xF8, 0x39, 0x9A, 0x51, 0x82, 0xF4, 0x65, 0x25, 0xEC, 0x35, 0x7D, 0x2F, 0x03, 0x43, 0x74, 0x03, 0xE0, 0xCB, 0x5D, 0xCA, 0x4A, + 0x13, 0xFD, 0x2F, 0x1B, 0x09, 0x20, 0x5B, 0x98, 0x90, 0xF0, 0x2E, 0xE5, 0xAF, 0x54, 0x29, 0x43, 0xE6, 0xF9, 0x37, 0x5E, 0xD0, 0x8A, 0x38, 0x53, 0x30, 0x42, 0xD6, 0xBB, 0xD5, 0x0F, 0x37, 0x25, + 0x1B, 0x15, 0x90, 0xF6, 0x3B, 0x4B, 0x58, 0xA7, 0xD1, 0xE1, 0xF3, 0x1C, 0xE6, 0x2E, 0x3D, 0x2A, 0xA9, 0x1E, 0x1C, 0x76, 0x7B, 0x9C, 0x3F, 0x5C, 0xB2, 0x68, 0x23, 0xF9, 0x7A, 0xD1, 0xD9, 0xFF, + 0xAB, 0x28, 0x75, 0xEB, 0x68, 0xFF, 0xA9, 0xB0, 0x99, 0x46, 0xEF, 0x1D, 0x70, 0x12, 0xC0, 0x29, 0x19, 0xEF, 0x13, 0xCB, 0x10, 0x0C, 0x2E, 0x2C, 0x79, 0x87, 0xA0, 0xA5, 0x78, 0x5B, 0x5F, 0x3F, + 0x3B, 0x94, 0x8B, 0x7F, 0xD6, 0x4B, 0x85, 0xB1, 0x65, 0xAE, 0x2F, 0xBF, 0x3C, 0x47, 0xE0, 0x39, 0xC3, 0x07, 0x3C, 0xA7, 0x8F, 0xC9, 0x00, 0xBB, 0xCD, 0xC0, 0x69, 0xFE, 0x90, 0x68, 0x85, 0xD5, + 0xB1, 0x37, 0x40, 0xA2, 0x23, 0xAF, 0x52, 0x54, 0xF9, 0x8C, 0x1D, 0x58, 0xE2, 0xFC, 0x92, 0xB0, 0x37, 0x3E, 0x2A, 0x93, 0x33, 0x53, 0xCC, 0x3E, 0xEC, 0xD3, 0x9F, 0x71, 0xD5, 0x9C, 0xFA, 0x09, + 0x29, 0x4E, 0x38, 0x26, 0x2A, 0x44, 0x89, 0x40, 0x0D, 0x22, 0x29, 0x82, 0xF9, 0xC7, 0x80, 0xCD, 0x07, 0x31, 0xD4, 0xEE, 0xD9, 0x16, 0xC5, 0xA3, 0x1A, 0xBC, 0xD0, 0x2A, 0x59, 0x0E, 0xD8, 0xC6, + 0xFF, 0xE1, 0x8B, 0x5F, 0xC7, 0xB6, 0x88, 0x8E, 0x74, 0x72, 0x69, 0x40, 0xD0, 0x2C, 0xCC, 0x62, 0xD7, 0x8B, 0xCA, 0xED, 0xDA, 0x2E, 0x02, 0x8E, 0x53, 0x5C, 0xDA, 0xFC, 0x0E, 0x09, 0x1B, 0xEF, + 0x50, 0xDE, 0x2D, 0xFD, 0x12, 0x4F, 0x1E, 0x85, 0x4F, 0x56, 0x85, 0x27, 0xAE, 0xF4, 0xDC, 0x84, 0x55, 0xFD, 0xA0, 0x1B, 0x6D, 0x0D, 0x43, 0x04, 0x8E, 0xD5, 0xAB, 0x42, 0xB1, 0xD4, 0x08, 0x13, + 0x99, 0x4B, 0x9F, 0x6A, 0xA0, 0xC0, 0x36, 0xC0, 0xDC, 0xF0, 0x8F, 0x46, 0xB0, 0x0F, 0xDA, 0x01, 0x44, 0x77, 0xCF, 0x87, 0x9B, 0x8F, 0xE5, 0xEA, 0xC4, 0x54, 0x1B, 0x82, 0xDA, 0x00, 0xB4, 0x34, + 0x60, 0x46, 0x86, 0x5B, 0x09, 0x2E, 0xD6, 0xAE, 0x01, 0x15, 0xFC, 0x83, 0x4B, 0x58, 0xF7, 0x5F, 0xF9, 0x28, 0xD7, 0xD9, 0x9A, 0xC8, 0x69, 0x1F, 0xF7, 0x00, 0x20, 0xAB, 0xA2, 0x54, 0x80, 0xAB, + 0xBC, 0xC7, 0x09, 0xE4, 0x6E, 0xC5, 0x10, 0xF4, 0xB8, 0xCA, 0xDD, 0x60, 0x04, 0x59, 0x54, 0xD3, 0xED, 0xDA, 0x7C, 0x23, 0xE0, 0x3D, 0x91, 0x69, 0x4D, 0x3C, 0x3E, 0xA2, 0x92, 0xC9, 0x25, 0x35, + 0xE6, 0xB5, 0xFE, 0x17, 0x1C, 0x56, 0x7D, 0xF3, 0x72, 0x94, 0x06, 0xCD, 0xBA, 0x2A, 0x5E, 0xFA, 0x59, 0xF1, 0x56, 0xE9, 0xCC, 0xD0, 0x30, 0x2F, 0xDC, 0x0F, 0x8B, 0xB7, 0x59, 0xB0, 0x5D, 0xFF, + 0x5D, 0xD8, 0x02, 0xCE, 0x4D, 0x55, 0x06, 0xA1, 0x9A, 0x69, 0xD7, 0x0B, 0x3A, 0xB4, 0x8A, 0xB1, 0x7A, 0x2F, 0xE5, 0x95, 0x89, 0xF7, 0x30, 0x83, 0xCC, 0xA5, 0x47, 0xFF, 0xB3, 0xF1, 0x46, 0x83, + 0xC9, 0x14, 0xBC, 0x13, 0x45, 0xE7, 0x38, 0x7E, 0x83, 0x1E, 0xE6, 0x03, 0x75, 0x01, 0x49, 0x5C, 0x92, 0xC3, 0x57, 0x70, 0x5A, 0x69, 0xF9, 0x52, 0xA2, 0xF7, 0xCD, 0x30, 0xE0, 0x33, 0x36, 0xAF, + 0xAA, 0xFC, 0x9C, 0x56, 0x60, 0x4C, 0xD5, 0x45, 0xE8, 0x2A, 0xA1, 0x2A, 0xF0, 0x58, 0xDA, 0xBA, 0x97, 0x43, 0x87, 0xFE, 0x8D, 0xCD, 0xEC, 0x69, 0x9A, 0x1E, 0x38, 0x53, 0xE2, 0x6D, 0x29, 0xE1, + 0x57, 0x81, 0x89, 0xAA, 0x8C, 0x2B, 0xBA, 0x15, 0x50, 0xDF, 0xBE, 0xDD, 0x1E, 0x4F, 0x22, 0x4E, 0xFC, 0xD6, 0x54, 0x91, 0xE5, 0x4E, 0x56, 0x12, 0x8A, 0xE7, 0xC2, 0xDC, 0x85, 0x66, 0x79, 0x7A, + 0xBF, 0x2D, 0x94, 0x55, 0x91, 0x52, 0x03, 0xA5, 0xC8, 0x9E, 0x55, 0xDD, 0x23, 0xDF, 0x82, 0x74, 0x36, 0xA8, 0xD6, 0xDC, 0xC5, 0xAC, 0xA8, 0x2F, 0x9B, 0x18, 0x36, 0x92, 0x15, 0x9E, 0xC0, 0x3F, + 0x2B, 0x79, 0x8E, 0x55, 0x7D, 0x14, 0x73, 0x46, 0xD8, 0x35, 0xA8, 0xD8, 0x1B, 0x2E, 0x3D, 0x40, 0x86, 0x39, 0x66, 0x86, 0x3A, 0x54, 0xD9, 0xC8, 0x7B, 0x5A, 0xAC, 0xE9, 0x63, 0xCD, 0x52, 0x9A, + 0xDB, 0xAE, 0x07, 0x07, 0x0C, 0xEA, 0x00, 0xB7, 0x80, 0xE1, 0x81, 0x31, 0xE6, 0x4F, 0x0A, 0xD7, 0x0E, 0x91, 0x58, 0xF5, 0x90, 0xD0, 0x0A, 0xD9, 0x17, 0x79, 0x08, 0xB9, 0x03, 0x45, 0xFD, 0x79, + 0xD0, 0x25, 0x57, 0x71, 0xC6, 0x08, 0xAF, 0x65, 0xEE, 0x5A, 0xC3, 0xC5, 0x01, 0x66, 0xBA, 0xD0, 0x57, 0x38, 0x02, 0x58, 0x68, 0x19, 0x41, 0x56, 0x0F, 0x11, 0x33, 0x40, 0x5F, 0xC2, 0xD7, 0x61, + 0x13, 0x14, 0xB4, 0x38, 0x1D, 0x54, 0x59, 0xDC, 0xDE, 0xDE, 0x4D, 0x39, 0xF3, 0x82, 0x3B, 0xC4, 0x42, 0x2B, 0xB1, 0xD7, 0x36, 0xE7, 0x47, 0x4A, 0x80, 0x89, 0xF0, 0xEC, 0xFA, 0x3C, 0x30, 0xAA, + 0xC1, 0x19, 0xFF, 0xA4, 0x2B, 0xF7, 0x43, 0xF4, 0x8E, 0x0F, 0xDD, 0x96, 0x02, 0x92, 0xD3, 0xE4, 0x9A, 0x14, 0xEB, 0x05, 0x90, 0xC8, 0xE0, 0x2E, 0x42, 0x1D, 0x54, 0xAE, 0x8A, 0x52, 0x19, 0x51, + 0x5E, 0x21, 0x89, 0x59, 0x89, 0xA0, 0xD7, 0x1D, 0x4F, 0x45, 0x16, 0x69, 0xCD, 0x65, 0x2D, 0xA3, 0x48, 0x9E, 0x5C, 0xDB, 0xC0, 0x87, 0x6B, 0xA0, 0xA0, 0x89, 0x9E, 0x7D, 0x87, 0x73, 0xB2, 0x4A, + 0xFC, 0x2C, 0xD6, 0xD3, 0x7C, 0xA3, 0x80, 0xA5, 0xD0, 0xDD, 0x43, 0x63, 0x04, 0xD6, 0xE1, 0xA4, 0xDC, 0xD6, 0x38, 0xE8, 0xB9, 0x5E, 0x6C, 0x95, 0x46, 0x5C, 0x66, 0x90, 0xD4, 0xEF, 0xE8, 0xF4, + 0x46, 0x91, 0xE4, 0x8D, 0xE2, 0x2C, 0xFC, 0x69, 0x1C, 0x75, 0x61, 0xAD, 0x8C, 0xC1, 0xA2, 0xC3, 0xCC, 0x9F, 0xB8, 0x6F, 0xF6, 0xF4, 0x70, 0x5A, 0x57, 0x3A, 0x72, 0x04, 0x71, 0xED, 0x33, 0xA0, + 0x0E, 0x8A, 0x60, 0x20, 0x38, 0x18, 0xA3, 0x96, 0x1E, 0x4D, 0x21, 0x3A, 0x78, 0xB8, 0x62, 0x63, 0x94, 0xF7, 0x5C, 0x28, 0x23, 0x15, 0x57, 0x4C, 0xCD, 0x72, 0x5A, 0x67, 0xE2, 0x0F, 0x0B, 0xF2, + 0x24, 0xBF, 0xFC, 0xAB, 0xD7, 0x02, 0xBF, 0xD4, 0xE1, 0xCC, 0x5F, 0x78, 0xBE, 0xC0, 0xE0, 0x42, 0xE1, 0x2E, 0xD4, 0xC9, 0x47, 0x4B, 0xDD, 0x5E, 0xED, 0x2A, 0xEB, 0x53, 0xF4, 0xA9, 0x58, 0xD7, + 0xF8, 0x4E, 0xFD, 0x56, 0xEC, 0x03, 0x0A, 0x94, 0xD2, 0x00, 0xA5, 0x39, 0xDE, 0x16, 0x4E, 0x53, 0xC8, 0x2A, 0xFE, 0x8C, 0x5F, 0x71, 0xBB, 0x99, 0xA0, 0x1F, 0x72, 0x30, 0xB7, 0xAE, 0xBC, 0x21, + 0x3E, 0xCD, 0xDB, 0xEF, 0x5B, 0x9E, 0x90, 0x64, 0x87, 0x43, 0x96, 0xF8, 0xA9, 0x1B, 0x05, 0x75, 0xF6, 0x8A, 0x45, 0x15, 0xDD, 0x15, 0x81, 0x78, 0xBF, 0x27, 0x7A, 0x90, 0xA3, 0xFE, 0xA2, 0x00, + 0x92, 0x00, 0xDA, 0x2E, 0xDA, 0x2C, 0x8B, 0x3A, 0x47, 0xC1, 0x04, 0xD3, 0x50, 0xDF, 0x68, 0xE9, 0x4C, 0x8A, 0x40, 0x23, 0xD3, 0xAE, 0xFB, 0xB7, 0x07, 0x18, 0xFA, 0x2E, 0x27, 0xE6, 0xA5, 0xC3, + 0xF9, 0x92, 0x7E, 0xC5, 0x96, 0xAB, 0x54, 0x0F, 0x46, 0x3A, 0xE0, 0x10, 0xEF, 0x71, 0xB8, 0x9B, 0x49, 0x49, 0x7F, 0x0C, 0xFD, 0x29, 0x39, 0xFF, 0xAB, 0x2A, 0x7D, 0xD1, 0x24, 0x7D, 0xC4, 0xA5, + 0x9D, 0x84, 0x11, 0xA8, 0x43, 0xBD, 0x84, 0xF1, 0xEA, 0x8D, 0xA3, 0x3C, 0x07, 0x01, 0xD7, 0x0A, 0xC2, 0x7C, 0x4B, 0xDB, 0xD0, 0xD9, 0xA0, 0xCA, 0xB8, 0x6B, 0x1F, 0xC5, 0xBE, 0x12, 0x45, 0x8A, + 0x25, 0x80, 0xA6, 0xCA, 0xB4, 0xB7, 0x65, 0xB8, 0x42, 0xC6, 0x7A, 0xD5, 0x4C, 0xA5, 0xD4, 0x0A, 0x24, 0xE2, 0xDD, 0xBC, 0xF0, 0x1E, 0x46, 0x6E, 0x08, 0xD9, 0xB3, 0x44, 0x9F, 0x13, 0xE8, 0x2E, + 0x16, 0xD6, 0x1C, 0x72, 0x3F, 0xB9, 0x46, 0x2E, 0x97, 0xB7, 0xAB, 0xC7, 0x0B, 0x22, 0x10, 0xEC, 0xA1, 0x6B, 0x16, 0x0D, 0x5B, 0x8F, 0x98, 0xA1, 0x79, 0x4D, 0xCA, 0x92, 0xCD, 0x4F, 0x02, 0x7F, + 0x3E, 0x41, 0x52, 0xEA, 0x87, 0x95, 0x07, 0xDD, 0xFE, 0x7F, 0x1F, 0x21, 0x51, 0x41, 0x53, 0xF0, 0x36, 0xAA, 0xBC, 0x33, 0xF1, 0x72, 0xC9, 0x5A, 0x9B, 0x77, 0x47, 0x22, 0x80, 0x0F, 0x2E, 0x08, + 0xCC, 0x44, 0xF9, 0x23, 0x54, 0x0D, 0x8A, 0xF6, 0x4B, 0x42, 0x99, 0x68, 0xB2, 0x80, 0x36, 0x4C, 0x1B, 0x7B, 0x4B, 0x3E, 0x9B, 0xEE, 0x40, 0xC5, 0x00, 0x02, 0x65, 0x7D, 0x99, 0x46, 0x31, 0xF3, + 0x3A, 0x8F, 0x8F, 0x13, 0x4A, 0x27, 0xEB, 0x69, 0xBA, 0x43, 0x95, 0x90, 0x8B, 0xA4, 0x06, 0x34, 0xB8, 0xF2, 0x70, 0x31, 0x49, 0x27, 0x5F, 0xFB, 0xBE, 0x8B, 0x48, 0x3E, 0xA1, 0xBB, 0xA9, 0x1C, + 0x28, 0x10, 0x51, 0x36, 0xD9, 0x7C, 0x47, 0x0E, 0xE8, 0x3C, 0xD2, 0x1C, 0xEB, 0x2B, 0x21, 0xAA, 0xED, 0x98, 0xDB, 0x8A, 0xB1, 0x65, 0xA7, 0xB4, 0xBE, 0x55, 0x9E, 0x7E, 0xAC, 0xA6, 0x84, 0x60, + 0x30, 0x15, 0xBC, 0x34, 0x9B, 0x0A, 0x51, 0x21, 0x4E, 0x4E, 0x8F, 0xBE, 0x1D, 0x2D, 0x88, 0x3F, 0x79, 0xFD, 0x3F, 0x1E, 0xDC, 0xDD, 0x3F, 0xA6, 0xD4, 0xB5, 0xBB, 0xD2, 0xA5, 0xB3, 0x00, 0x3A, + 0x80, 0xF1, 0xDA, 0xDE, 0x97, 0x5B, 0x50, 0x2C, 0x7F, 0x72, 0x03, 0x73, 0x16, 0xBC, 0x55, 0xC1, 0xE5, 0x7E, 0x50, 0x06, 0x27, 0xD6, 0x0E, 0x31, 0x08, 0x74, 0x31, 0xD2, 0xC9, 0xD0, 0x2C, 0xA9, + 0xF0, 0xEB, 0xCC, 0xD4, 0xBF, 0xE3, 0xC4, 0xBB, 0x53, 0x6D, 0x4C, 0xFE, 0xF7, 0x51, 0x07, 0x50, 0x45, 0x2D, 0x44, 0x4B, 0xE2, 0xC3, 0xD6, 0x4D, 0x84, 0xA8, 0x32, 0x96, 0x53, 0x05, 0x26, 0x4A, + 0xBB, 0x53, 0xE3, 0x61, 0x49, 0x40, 0xF9, 0xB2, 0xF1, 0xEA, 0x6F, 0x41, 0xCA, 0x8F, 0x69, 0xE7, 0x26, 0x69, 0x0B, 0xA6, 0x30, 0x63, 0x0F, 0x8A, 0x91, 0x6E, 0xE8, 0x56, 0x26, 0x82, 0x51, 0xB7, + 0x73, 0xDC, 0x2A, 0x5D, 0xB4, 0x5D, 0x22, 0xDF, 0xB2, 0x43, 0x9C, 0xA4, 0xB7, 0xAB, 0x70, 0x21, 0x5D, 0x23, 0xE1, 0xF2, 0xE2, 0x61, 0x73, 0x94, 0xFF, 0x78, 0x3B, 0x0B, 0xFF, 0x6D, 0xF0, 0x34, + 0x5C, 0xC9, 0x27, 0x05, 0x3D, 0x02, 0xC6, 0x5F, 0xE2, 0xA8, 0x6D, 0xEF, 0xBE, 0xBF, 0x52, 0x43, 0xA2, 0xEF, 0x6A, 0x63, 0x12, 0xBA, 0xED, 0xB6, 0xE6, 0x0D, 0xBB, 0x0C, 0x67, 0xCC, 0x9A, 0x65, + 0x55, 0x85, 0xCB, 0x45, 0x8D, 0x6A, 0x04, 0x18, 0x11, 0x94, 0x81, 0x5F, 0x03, 0xBE, 0x87, 0xF6, 0xE8, 0x00, 0x49, 0x2A, 0x24, 0xC5, 0xD5, 0x02, 0xD5, 0xEC, 0xD5, 0x3D, 0xD6, 0xDA, 0x36, 0x79, + 0x95, 0xD3, 0x2E, 0x8B, 0xBA, 0xA3, 0xEF, 0x62, 0x72, 0x7E, 0x8A, 0x61, 0x0E, 0x8D, 0x6B, 0x5C, 0x8F, 0xAB, 0xCB, 0xE8, 0x89, 0x3B, 0xDB, 0x5E, 0x03, 0x86, 0x27, 0xF7, 0x07, 0xE8, 0x46, 0x4C, + 0x55, 0xDC, 0xBB, 0x76, 0xF0, 0x83, 0x6A, 0xDD, 0x29, 0x8A, 0x96, 0x7C, 0x45, 0x95, 0x08, 0xBC, 0x4E, 0x88, 0xBA, 0x5C, 0xA3, 0x8F, 0x5A, 0x56, 0x1A, 0x6D, 0x2D, 0x6C, 0xB2, 0x17, 0x8D, 0x90, + 0xAC, 0x85, 0x0C, 0xA2, 0x73, 0x4B, 0x45, 0xC4, 0xA8, 0x9A, 0xA0, 0xF1, 0x52, 0xA3, 0xB5, 0x3B, 0xCF, 0x1E, 0x13, 0x53, 0x2B, 0x2B, 0x5B, 0x38, 0x78, 0xB2, 0x05, 0xBD, 0x2B, 0x32, 0x7D, 0xC4, + 0x9E, 0xB6, 0x66, 0x0B, 0x95, 0x11, 0xBF, 0xAE, 0x90, 0xC1, 0xDE, 0xA5, 0xBD, 0xEB, 0x6D, 0xC5, 0xDA, 0x06, 0x8B, 0xCB, 0xDC, 0x6C, 0x09, 0x3E, 0x57, 0x27, 0xE3, 0x87, 0x37, 0x4F, 0x45, 0x2F, + 0x96, 0x3C, 0x30, 0x7D, 0xEE, 0x86, 0x5D, 0x41, 0xAA, 0x12, 0x4C, 0xA8, 0x03, 0xC1, 0x2F, 0x9A, 0xE9, 0x29, 0x9C, 0x3C, 0xB1, 0x34, 0x5F, 0xCC, 0x56, 0x8C, 0x6E, 0x71, 0xBE, 0x33, 0x66, 0xBF, + 0x30, 0xEF, 0xEE, 0xEF, 0xC7, 0x69, 0x3C, 0x36, 0xAC, 0xE5, 0x76, 0xB0, 0xD1, 0x0F, 0x40, 0x2F, 0x38, 0x00, 0x09, 0xFD, 0x0E, 0xC0, 0x68, 0xCB, 0x2D, 0x45, 0x98, 0x48, 0x84, 0xED, 0xF1, 0x6B, + 0xC9, 0x0B, 0x0F, 0xF6, 0xDC, 0x96, 0x30, 0x9E, 0xA3, 0x77, 0xA3, 0xCE, 0xC0, 0x43, 0xCB, 0x76, 0xB6, 0xC8, 0x85, 0xBB, 0xB8, 0x48, 0xC4, 0x74, 0x5B, 0x71, 0xE1, 0x8C, 0x58, 0xE7, 0x80, 0x50, + 0xE1, 0x9B, 0xD7, 0xBE, 0x08, 0x31, 0xEF, 0xE9, 0x05, 0x2A, 0x6A, 0x7D, 0xF8, 0xD4, 0xE8, 0xB9, 0xFC, 0x3E, 0x08, 0x2A, 0x4D, 0x40, 0xAD, 0x73, 0xE4, 0xB3, 0x18, 0x5E, 0x2F, 0x6D, 0xED, 0xE7, + 0xEE, 0x51, 0xA4, 0x06, 0x8F, 0xF2, 0xDA, 0x57, 0x37, 0x3F, 0xD7, 0xE7, 0xBD, 0x46, 0xE0, 0x08, 0x0F, 0x4C, 0x2C, 0x1F, 0x41, 0xBC, 0x25, 0x0E, 0x6D, 0xA4, 0x5A, 0x34, 0x1F, 0x21, 0x47, 0x71, + 0xF5, 0x53, 0x1A, 0x67, 0xB0, 0xFD, 0x97, 0xB5, 0x3C, 0xD7, 0x2C, 0xFA, 0xC7, 0x21, 0x5B, 0xC4, 0x11, 0x1F, 0x09, 0x40, 0x30, 0xA9, 0x13, 0x83, 0xD2, 0x01, 0x82, 0x21, 0x0F, 0xCE, 0xCD, 0x75, + 0xE5, 0x9C, 0x4B, 0x0B, 0x33, 0xA3, 0xF9, 0x3D, 0x86, 0x5D, 0x84, 0x7E, 0xC2, 0x41, 0xE1, 0xB9, 0x84, 0x81, 0xC5, 0xD9, 0xD2, 0x7F, 0x0A, 0xE2, 0x62, 0xB3, 0x28, 0x65, 0x0C, 0xDC, 0x13, 0xCD, + 0x99, 0x86, 0x6B, 0xE9, 0xA5, 0xA0, 0x30, 0xE8, 0x3D, 0x84, 0xE3, 0x2B, 0xD2, 0x13, 0xC9, 0x4B, 0xD6, 0xAF, 0x95, 0x04, 0x33, 0xA4, 0xF0, 0x0C, 0x61, 0x49, 0x78, 0x3B, 0x00, 0x75, 0x0C, 0xDF, + 0xD4, 0xF4, 0x7A, 0xE7, 0x52, 0x17, 0xEE, 0xD1, 0xF6, 0x0C, 0x36, 0x6F, 0xA0, 0x2C, 0xDB, 0x20, 0x6F, 0xEB, 0x2A, 0x68, 0x5D, 0x6B, 0x7D, 0x6A, 0x4C, 0x13, 0x55, 0x3E, 0x2B, 0xE2, 0x77, 0x94, + 0xF5, 0x3B, 0x0E, 0xF5, 0x73, 0x15, 0x20, 0x32, 0x63, 0xEB, 0x02, 0x6E, 0xA5, 0xE6, 0x70, 0x67, 0xD2, 0x2F, 0x92, 0xE2, 0x6E, 0x98, 0xDF, 0x9A, 0xB3, 0x86, 0xC2, 0x70, 0x5B, 0x43, 0x16, 0xA6, + 0x98, 0x92, 0x68, 0x8E, 0x60, 0x1E, 0x74, 0x27, 0x59, 0x5A, 0xCE, 0xE6, 0xE4, 0x7F, 0x5E, 0xC5, 0x98, 0xCC, 0x48, 0xC2, 0xF2, 0xDA, 0x1C, 0x32, 0xE0, 0x62, 0xA3, 0x49, 0xD8, 0x9D, 0xCC, 0x8C, + 0x05, 0xC6, 0x2E, 0x7B, 0x0C, 0xED, 0x6F, 0x2E, 0x93, 0xA7, 0xBD, 0x48, 0xA8, 0x00, 0x4A, 0x8C, 0x5C, 0x60, 0x5D, 0xFF, 0xC8, 0x05, 0xDE, 0x07, 0x9E, 0xDE, 0xE7, 0xCE, 0xD9, 0x86, 0x39, 0xA9, + 0x2F, 0x6C, 0xBA, 0x92, 0xF2, 0x08, 0x9B, 0x14, 0x5D, 0x2D, 0x61, 0xD9, 0x63, 0x8C, 0x07, 0x34, 0x7A, 0x2E, 0xF6, 0xB3, 0x0F, 0xD9, 0x0E, 0x11, 0x1A, 0x7F, 0x59, 0x13, 0xF6, 0xE1, 0x87, 0x95, + 0xC1, 0x9E, 0x0B, 0x9F, 0x60, 0xF8, 0x5B, 0xD8, 0xF5, 0xC9, 0xA9, 0x63, 0x33, 0x94, 0x41, 0xE4, 0xA5, 0xB7, 0x9E, 0xB2, 0xE8, 0x67, 0x96, 0x1B, 0x18, 0xA1, 0x88, 0x4A, 0x01, 0xA7, 0x44, 0x83, + 0xD8, 0x0B, 0x40, 0x3E, 0xFB, 0xDB, 0xD4, 0xED, 0xDD, 0xC1, 0x92, 0x2D, 0xA3, 0xFB, 0xB3, 0x7B, 0xEA, 0x97, 0xE0, 0xA5, 0xB6, 0x34, 0x3E, 0x43, 0x67, 0x60, 0x1B, 0xD2, 0x1D, 0xB6, 0x69, 0x41, + 0xC2, 0x69, 0x8B, 0xF5, 0x06, 0xB0, 0x48, 0x61, 0xB5, 0xF3, 0xD3, 0xD8, 0x0A, 0xC6, 0xDC, 0xB6, 0x84, 0xD9, 0xC4, 0x36, 0x9A, 0xBD, 0x04, 0xBC, 0x4B, 0xDB, 0xEF, 0x49, 0xC6, 0x6E, 0x38, 0x44, + 0x51, 0x3A, 0x3F, 0x3B, 0xDD, 0x40, 0x0C, 0x08, 0x0A, 0xC6, 0xEA, 0xD8, 0x1E, 0x8B, 0xB0, 0xE7, 0xCB, 0x36, 0xDB, 0x7B, 0x7E, 0xAB, 0x47, 0x28, 0x39, 0x18, 0x57, 0xF5, 0x97, 0xA3, 0x46, 0x48, + 0x63, 0xC3, 0x12, 0x64, 0x5B, 0x20, 0xAF, 0x02, 0xF7, 0xD0, 0xBD, 0x9A, 0x74, 0xDE, 0x23, 0x61, 0xA0, 0xD2, 0xD9, 0x8A, 0x69, 0x89, 0x75, 0xB3, 0x0F, 0x10, 0x10, 0xD9, 0x0A, 0x12, 0x60, 0x78, + 0x58, 0x4A, 0x45, 0xFF, 0xBC, 0xC6, 0x5B, 0x47, 0x97, 0x6A, 0xF6, 0x57, 0xEA, 0x84, 0xE9, 0x73, 0x0D, 0x9E, 0x36, 0x37, 0x33, 0x73, 0x6A, 0xC8, 0x01, 0x03, 0xDC, 0x1C, 0x75, 0x73, 0xC4, 0xDE, + 0xE2, 0x8A, 0x7B, 0xAC, 0x9E, 0xF7, 0x2C, 0xB8, 0x29, 0x45, 0x0B, 0x53, 0xEA, 0xF9, 0x84, 0xCD, 0x01, 0xAA, 0x31, 0x41, 0x6C, 0xE8, 0x91, 0x4B, 0x7D, 0x7E, 0xF8, 0x49, 0xEB, 0x9C, 0xC1, 0x72, + 0xD7, 0x09, 0x6D, 0xEF, 0xDA, 0xCF, 0x59, 0x6B, 0x9B, 0x21, 0xA5, 0x73, 0xE3, 0x46, 0xA4, 0x7A, 0x5A, 0x46, 0x9E, 0x1D, 0x79, 0x39, 0xBE, 0x19, 0x82, 0xCB, 0x39, 0x54, 0xC2, 0x14, 0xED, 0x3A, + 0x37, 0x07, 0xD7, 0x40, 0xC0, 0x33, 0xE3, 0xEF, 0x78, 0x0F, 0x4C, 0x48, 0xBA, 0xDD, 0x86, 0x38, 0x48, 0xBB, 0xFC, 0x9D, 0xAA, 0x8E, 0x38, 0x06, 0xA8, 0x4B, 0x2C, 0xAC, 0x0C, 0xA2, 0x32, 0x00, + 0x0C, 0xAF, 0x02, 0x03, 0xE9, 0x08, 0xFC, 0xE1, 0x8B, 0x5D, 0x62, 0x77, 0x72, 0x25, 0xD2, 0xD7, 0xD5, 0x84, 0xF2, 0xED, 0x71, 0x88, 0x5D, 0xFA, 0xF5, 0xA4, 0xDB, 0xEE, 0x02, 0xF2, 0x85, 0xBC, + 0x34, 0x55, 0x9B, 0x88, 0xEA, 0x9C, 0xE1, 0x5B, 0x47, 0xA3, 0xB9, 0x2A, 0x8D, 0x6F, 0x91, 0x59, 0x1C, 0x32, 0x9A, 0x5A, 0xA2, 0x1A, 0x1B, 0xC4, 0x24, 0xBA, 0x2B, 0xDB, 0xD1, 0x64, 0xCE, 0x1A, + 0x8B, 0x78, 0xB3, 0x8B, 0xEF, 0x2B, 0x47, 0xF2, 0x1F, 0x7F, 0xB7, 0xA3, 0xC5, 0x4E, 0x3E, 0xA4, 0x53, 0x6E, 0x81, 0x6E, 0x01, 0x65, 0x6C, 0x8E, 0x26, 0xAD, 0x42, 0xF3, 0xCB, 0x90, 0x61, 0x69, + 0x67, 0xC0, 0xDD, 0x07, 0x9F, 0x95, 0x6C, 0x9F, 0x3C, 0x84, 0x4D, 0x5F, 0x33, 0x9C, 0x62, 0xEE, 0x8A, 0x35, 0x8C, 0x4B, 0xEC, 0x2D, 0x27, 0x8A, 0xF7, 0x18, 0xAD, 0x50, 0x9C, 0x6B, 0x66, 0x61, + 0x3B, 0x58, 0x04, 0x43, 0xFA, 0x6F, 0x11, 0xCD, 0x8D, 0x10, 0x76, 0x93, 0xB5, 0xD7, 0xB7, 0x38, 0xAA, 0x7E, 0x2F, 0xE6, 0x62, 0x50, 0x2D, 0x75, 0x04, 0xA9, 0xF5, 0x96, 0x19, 0x41, 0x80, 0xF8, + 0x70, 0x0D, 0xC4, 0xE6, 0xF7, 0xE8, 0xE7, 0xD2, 0x30, 0x72, 0x34, 0x49, 0x4B, 0x8D, 0xF1, 0xD5, 0x7E, 0xE1, 0x4D, 0x6C, 0x97, 0x92, 0x6E, 0xB1, 0xD8, 0x90, 0x4D, 0x80, 0x89, 0xBE, 0x7D, 0x13, + 0x5B, 0x13, 0xD6, 0xDE, 0x30, 0xAA, 0x87, 0x20, 0xD6, 0x71, 0x59, 0xBB, 0x50, 0xA8, 0x34, 0xDE, 0x90, 0x79, 0x92, 0x2B, 0x88, 0x93, 0x1D, 0x45, 0x85, 0x00, 0x62, 0x68, 0x34, 0xDA, 0x04, 0x0D, + 0xB7, 0x68, 0xDD, 0xDB, 0xE6, 0x7A, 0x75, 0x8A, 0x02, 0xB4, 0x48, 0xE3, 0x6B, 0xA4, 0x55, 0x03, 0x4A, 0xDE, 0x36, 0x80, 0x2A, 0xA4, 0x2A, 0x7F, 0x2F, 0x23, 0x4A, 0x5E, 0x1C, 0xC2, 0x41, 0xE5, + 0x66, 0x1C, 0x63, 0xAF, 0xCE, 0x59, 0xDF, 0xDC, 0xC0, 0x89, 0x83, 0x47, 0xD2, 0x83, 0x4D, 0x72, 0x64, 0xF5, 0xB2, 0x1A, 0x47, 0xC5, 0x21, 0x4A, 0xDC, 0x57, 0xAF, 0x76, 0xCE, 0x9E, 0xBD, 0xB6, + 0x8C, 0x71, 0x02, 0x9B, 0xCF, 0x0C, 0x4C, 0x74, 0x5A, 0x33, 0x45, 0x4A, 0xCF, 0x0C, 0xF6, 0xD5, 0xC6, 0x8D, 0xEA, 0x06, 0xC4, 0x5E, 0x7D, 0x4D, 0x17, 0x55, 0xC5, 0xAC, 0xDC, 0x37, 0xFC, 0x24, + 0x34, 0x14, 0x0E, 0xF7, 0x07, 0xFD, 0x55, 0xFA, 0xF0, 0x6C, 0xBB, 0x17, 0x07, 0xC2, 0x7C, 0xE9, 0xD9, 0x05, 0x90, 0x5E, 0x37, 0xE2, 0xF1, 0x47, 0xC9, 0xCB, 0x88, 0x08, 0xEC, 0xD0, 0x5D, 0xF7, + 0x1F, 0xC5, 0xF1, 0xDA, 0xF9, 0x10, 0xD7, 0xBD, 0x68, 0xB6, 0x91, 0x49, 0x38, 0xBF, 0x0C, 0xAB, 0xCF, 0x66, 0xC9, 0x05, 0xC4, 0x95, 0x63, 0xD7, 0xD7, 0x0F, 0x2C, 0x3D, 0x3A, 0x4A, 0x4F, 0x62, + 0x9E, 0x3A, 0xFD, 0xE5, 0x3B, 0xD1, 0x4C, 0xD6, 0xE5, 0x27, 0xE4, 0xF0, 0x38, 0xD6, 0xA3, 0x31, 0xD0, 0x14, 0x68, 0xE2, 0x2D, 0xFE, 0x93, 0xA3, 0x79, 0xB3, 0xEC, 0x6D, 0xA6, 0xD1, 0xC2, 0xF6, + 0xD5, 0xEA, 0xB1, 0x41, 0xE5, 0x75, 0xF9, 0x3C, 0x8C, 0xC5, 0x58, 0x0D, 0xF4, 0xA3, 0xDB, 0x5C, 0x4C, 0x87, 0xD8, 0x54, 0x8E, 0x9A, 0x85, 0x19, 0x46, 0xD1, 0xB9, 0x0D, 0x75, 0x27, 0x40, 0x7F, + 0x1B, 0xA1, 0x12, 0x1E, 0xAC, 0x54, 0xA1, 0x1E, 0x6E, 0xDA, 0x45, 0xAB, 0xB0, 0x8A, 0x7A, 0x78, 0xAB, 0x36, 0xA7, 0x6E, 0xAD, 0x7F, 0xAC, 0x46, 0x78, 0xE5, 0x24, 0x64, 0xEF, 0xF3, 0x98, 0xE9, + 0x02, 0x15, 0xAC, 0x31, 0x6D, 0xE5, 0xA6, 0xEF, 0xE5, 0xA7, 0xB4, 0xA9, 0x5D, 0xF9, 0x2E, 0x41, 0x29, 0xF3, 0xF9, 0x1B, 0x31, 0x6F, 0x75, 0x67, 0x08, 0xBD, 0xF3, 0x7C, 0x01, 0xC1, 0x2B, 0xBA, + 0xA0, 0x91, 0xF9, 0x48, 0x84, 0xE3, 0x8A, 0xFF, 0x3C, 0x7B, 0x81, 0x40, 0x88, 0x8C, 0xAB, 0x4F, 0x7F, 0x86, 0x7E, 0xAD, 0xB0, 0x41, 0x85, 0x84, 0xB6, 0xF7, 0x70, 0x74, 0x02, 0x50, 0x93, 0x6A, + 0x13, 0x8A, 0xFF, 0x52, 0x88, 0x88, 0x40, 0x67, 0x7D, 0x81, 0x21, 0xC5, 0x83, 0x80, 0x6F, 0xE2, 0x71, 0x04, 0xDE, 0x52, 0x88, 0x13, 0xE5, 0x62, 0x26, 0xB6, 0x52, 0xC5, 0x86, 0x9B, 0xB5, 0x00, + 0x30, 0x38, 0x34, 0xD9, 0xC9, 0xD1, 0x97, 0xDB, 0xA1, 0xDD, 0x5C, 0x47, 0x34, 0x30, 0x7A, 0xB8, 0xBD, 0x00, 0x6B, 0x66, 0xEF, 0x45, 0xAB, 0xED, 0x2E, 0x31, 0x37, 0x7B, 0xEA, 0xA1, 0x9D, 0xAE, + 0x6E, 0xC8, 0x2A, 0xD7, 0x7C, 0x4C, 0x07, 0x74, 0x4F, 0x9B, 0x93, 0xA8, 0xDD, 0x4C, 0xEE, 0x1A, 0x62, 0xA5, 0x52, 0xED, 0xF4, 0xE2, 0x77, 0xCA, 0xCF, 0xF1, 0xF9, 0x64, 0xDA, 0x7A, 0xF8, 0xFA, + 0xFF, 0x6B, 0x56, 0xE3, 0xEB, 0xC0, 0x68, 0x50, 0xA9, 0xF7, 0x6E, 0xCF, 0xB2, 0xC2, 0xBA, 0xA6, 0x60, 0x95, 0x8C, 0x6D, 0x1B, 0xA9, 0x6B, 0xA8, 0x57, 0x8D, 0x06, 0x6D, 0x6A, 0xFE, 0x6E, 0x8F, + 0xB2, 0x05, 0x2B, 0x74, 0x21, 0xD5, 0x7D, 0xE5, 0xAB, 0x4C, 0x1F, 0xD5, 0x51, 0x70, 0xE9, 0xEE, 0x33, 0xEB, 0x32, 0xFB, 0x3D, 0x2C, 0x88, 0x61, 0x42, 0x05, 0x5E, 0xE8, 0x42, 0x8B, 0xD7, 0x45, + 0xAA, 0xBE, 0x1D, 0x15, 0x19, 0x1F, 0xFC, 0x93, 0xA3, 0xFA, 0x7A, 0x86, 0xB4, 0x27, 0xEB, 0x23, 0x70, 0xB7, 0x8A, 0x67, 0xA4, 0x85, 0xAF, 0x96, 0x3B, 0xBE, 0x1F, 0x22, 0x46, 0x11, 0x9F, 0xB4, + 0x69, 0xA0, 0x02, 0xD7, 0x02, 0x9F, 0xC4, 0xF5, 0xF7, 0xE0, 0x12, 0x5F, 0xDA, 0x73, 0x05, 0xAC, 0xF6, 0xC8, 0x0C, 0x7B, 0xD3, 0xF6, 0x68, 0x89, 0x7B, 0xA8, 0x14, 0x35, 0xF4, 0x26, 0xB8, 0x42, + 0x5C, 0x98, 0x55, 0xCD, 0x46, 0xC3, 0x44, 0x8B, 0xBA, 0xD0, 0x73, 0x9B, 0xA8, 0x8A, 0xBC, 0x27, 0x3B, 0xCD, 0x0F, 0xA1, 0xFD, 0xA7, 0xF4, 0xF8, 0x18, 0x3B, 0x5D, 0x73, 0xD1, 0x6C, 0x40, 0x7C, + 0x45, 0x2A, 0xEF, 0xA2, 0xE3, 0xCA, 0x9F, 0x2D, 0x9D, 0x63, 0x8D, 0x96, 0x6A, 0x58, 0x78, 0x8B, 0x48, 0xBF, 0xC5, 0x7D, 0x3F, 0xC2, 0x08, 0x5F, 0xE8, 0x5A, 0x7F, 0x7A, 0xDD, 0xD9, 0x1E, 0xFD, + 0x1B, 0xA0, 0x22, 0x60, 0x46, 0xB1, 0x27, 0xA9, 0x7B, 0xC4, 0x80, 0x47, 0x9B, 0x92, 0x88, 0x1A, 0x58, 0xA0, 0xBC, 0x04, 0xD8, 0xDD, 0x9E, 0x68, 0xB6, 0xD2, 0xBC, 0x50, 0x34, 0xCF, 0x23, 0x43, + 0x0D, 0x1F, 0xE5, 0x49, 0x91, 0xA6, 0x90, 0x8B, 0x01, 0x9E, 0xE0, 0x18, 0xC8, 0x43, 0xB9, 0xFA, 0x53, 0xEC, 0x7E, 0xE5, 0xF1, 0x14, 0xAB, 0xE2, 0xB7, 0x50, 0xD4, 0xE1, 0xE7, 0x2E, 0xAF, 0xB4, + 0xFB, 0xB3, 0x3A, 0x1E, 0x2C, 0x4D, 0x62, 0x72, 0xCE, 0xE2, 0x7B, 0xBB, 0x13, 0xB5, 0xD2, 0x3E, 0x24, 0xF6, 0x12, 0x9C, 0xF5, 0x82, 0x5F, 0x34, 0xAF, 0xC0, 0x56, 0xF9, 0x5F, 0x53, 0xA0, 0x9F, + 0x6F, 0xCA, 0x94, 0x35, 0xCD, 0x5F, 0xB6, 0xC0, 0x5F, 0x88, 0xB4, 0xDC, 0xE8, 0x6C, 0xEA, 0xBD, 0x7E, 0x0C, 0x78, 0x53, 0x61, 0xD2, 0x53, 0xBB, 0x9C, 0xDB, 0x3A, 0x0C, 0x6B, 0xC8, 0x51, 0x83, + 0x01, 0xFF, 0x44, 0xF9, 0xE8, 0x7F, 0x7A, 0x97, 0xEC, 0x9F, 0x02, 0xFA, 0xB5, 0x13, 0x4F, 0x3B, 0xBF, 0xA1, 0xCB, 0xE4, 0x4F, 0xA8, 0x3F, 0x1C, 0x54, 0x3E, 0xD9, 0xB8, 0x70, 0x65, 0x75, 0x43, + 0x5A, 0xC6, 0xA1, 0x5F, 0x7B, 0x0D, 0xEB, 0xA9, 0xD4, 0x5A, 0xF5, 0x54, 0xBB, 0x0C, 0xCB, 0xCA, 0x12, 0xA6, 0xC1, 0x6E, 0x5E, 0xE6, 0xFA, 0xD6, 0x37, 0x21, 0xE4, 0xC3, 0xCC, 0x8D, 0x9E, 0xA6, + 0x8C, 0x61, 0x49, 0x99, 0x30, 0x80, 0x95, 0x24, 0x07, 0xAF, 0xA2, 0x03, 0xF5, 0x04, 0xA8, 0x87, 0xB3, 0xBF, 0x84, 0xD2, 0xBB, 0x6E, 0x45, 0xE7, 0xCC, 0x53, 0x26, 0x53, 0x3D, 0x63, 0x96, 0x3F, + 0xFB, 0x72, 0xA9, 0x27, 0x2C, 0x8F, 0xF6, 0x37, 0xBE, 0x6E, 0x24, 0x73, 0xE9, 0xFC, 0xAB, 0x6B, 0x5E, 0x5E, 0x7C, 0xF3, 0xED, 0xBD, 0xDA, 0xEF, 0x51, 0xC9, 0x8D, 0x53, 0x17, 0x0F, 0x9B, 0x64, + 0xBC, 0xA5, 0xD4, 0x9F, 0x76, 0xAF, 0x17, 0x6D, 0x01, 0xA6, 0xF2, 0xEC, 0xB3, 0x39, 0x15, 0x1F, 0x49, 0xE4, 0x9A, 0x8F, 0x6E, 0x28, 0x6C, 0x6D, 0x41, 0x22, 0xD6, 0x50, 0xD5, 0x01, 0x59, 0x10, + 0xFF, 0x7F, 0x28, 0x02, 0x46, 0x93, 0x89, 0x5C, 0x58, 0x03, 0xDD, 0xFF, 0xCB, 0x1E, 0xDC, 0x46, 0x79, 0xC8, 0xF5, 0x35, 0xAC, 0x15, 0x97, 0xD9, 0xB2, 0x8A, 0xC4, 0x6E, 0x62, 0x88, 0x81, 0x01, + 0x29, 0xC1, 0x79, 0x55, 0x6A, 0xF7, 0x88, 0x2D, 0xEE, 0x17, 0xD5, 0x8A, 0x97, 0xF4, 0x34, 0xDF, 0x83, 0x64, 0x6B, 0x33, 0xCF, 0xBA, 0xB9, 0x0A, 0x62, 0x50, 0x85, 0x1C, 0xF5, 0x3D, 0x4B, 0xDB, + 0x45, 0x26, 0x33, 0x7D, 0xCC, 0xB9, 0xD9, 0x8A, 0x92, 0x16, 0x76, 0xB5, 0x13, 0x65, 0xDD, 0x08, 0xA5, 0x30, 0x4D, 0x2A, 0x93, 0x53, 0x4C, 0x52, 0x42, 0x7E, 0x9A, 0xE5, 0xC1, 0x44, 0x05, 0x92, + 0xC5, 0x53, 0x6E, 0x17, 0x1C, 0xF4, 0xFD, 0x1F, 0x43, 0x57, 0x8F, 0xEA, 0xFB, 0x32, 0xFF, 0x01, 0xD4, 0xFE, 0xD6, 0x35, 0xD7, 0x52, 0x56, 0x8F, 0x90, 0xEC, 0xFB, 0xB1, 0x64, 0xA5, 0xB1, 0x76, + 0x3F, 0x70, 0xC7, 0x2F, 0xD5, 0xBC, 0xDF, 0x61, 0xD0, 0x1F, 0xF3, 0x23, 0x66, 0x39, 0xC9, 0x1C, 0x06, 0x3C, 0x0B, 0x7A, 0x56, 0xAD, 0x03, 0xF4, 0x02, 0x0E, 0x80, 0xBD, 0x9A, 0x5E, 0x2F, 0x16, + 0x1E, 0x05, 0x78, 0x46, 0x9B, 0x99, 0x50, 0x26, 0x6B, 0xA9, 0x6B, 0xBB, 0x73, 0xC0, 0x8E, 0x7F, 0xAE, 0x85, 0x6E, 0x17, 0x03, 0xCF, 0x3C, 0xBD, 0x21, 0x41, 0x80, 0x89, 0x14, 0x8F, 0x7A, 0x9F, + 0x40, 0xD4, 0xD9, 0x11, 0x51, 0xDB, 0xC4, 0xBA, 0xE8, 0x54, 0x23, 0x59, 0xE8, 0x82, 0xA1, 0x9A, 0x99, 0x49, 0xCE, 0xD5, 0xB7, 0x5F, 0xF7, 0xB1, 0x92, 0xDC, 0x27, 0x9B, 0x3E, 0xD1, 0x00, 0x76, + 0x05, 0x3F, 0x58, 0xDE, 0x43, 0x5F, 0xC5, 0x87, 0x56, 0x54, 0xE9, 0x86, 0x33, 0xA3, 0x97, 0x14, 0x11, 0x42, 0x22, 0x9D, 0x8C, 0xD6, 0x13, 0xC6, 0x63, 0x44, 0x32, 0x6D, 0x83, 0x99, 0x2B, 0x3C, + 0x08, 0xF1, 0x7B, 0xE0, 0xEC, 0x28, 0xFB, 0xDB, 0xAB, 0xA1, 0x2C, 0xB0, 0x00, 0xB2, 0xA2, 0xB0, 0x4E, 0x24, 0xD0, 0xC4, 0x1B, 0xD6, 0xB5, 0x80, 0xE9, 0x99, 0xB2, 0x57, 0xC0, 0x07, 0x96, 0x5C, + 0x44, 0x75, 0xA9, 0xD5, 0x31, 0x4C, 0xD6, 0xC1, 0xFB, 0x9F, 0xED, 0xD5, 0x16, 0xE6, 0xB3, 0xC0, 0xDD, 0xD4, 0x04, 0xD6, 0x8D, 0x78, 0xFD, 0x4D, 0xE4, 0x09, 0x31, 0xB1, 0xB8, 0x72, 0xD4, 0xD0, + 0x1A, 0x2D, 0x46, 0xC9, 0xB2, 0x93, 0x90, 0x0D, 0x34, 0xEC, 0x91, 0xD3, 0xB6, 0x93, 0xF4, 0xE7, 0x2C, 0x22, 0x8E, 0xD0, 0x29, 0x4F, 0x6D, 0xC9, 0xB7, 0x17, 0x26, 0x0E, 0xBE, 0x75, 0xA4, 0x71, + 0xEA, 0x4D, 0x78, 0x00, 0xA3, 0xE7, 0xB7, 0xB4, 0x76, 0xD6, 0x4D, 0xEA, 0x6F, 0x4D, 0xA7, 0x26, 0xB3, 0x76, 0xF0, 0x78, 0x00, 0xDB, 0x5F, 0x83, 0xC0, 0xA3, 0xDC, 0xC2, 0xC7, 0x02, 0x6A, 0x4C, + 0x37, 0x8E, 0x88, 0x09, 0x94, 0x88, 0x5D, 0x6F, 0x7A, 0x88, 0x19, 0xD9, 0x1A, 0x2D, 0x50, 0xD1, 0x6D, 0x22, 0xBE, 0x59, 0x2B, 0xED, 0x38, 0x33, 0x04, 0x10, 0xE1, 0x4C, 0xDD, 0xD4, 0xCE, 0x0C, + 0x48, 0xD6, 0x2B, 0x77, 0x97, 0xDE, 0x44, 0xC0, 0x7F, 0x26, 0xA7, 0x9E, 0xF3, 0xA5, 0x83, 0x0F, 0x32, 0x1A, 0x35, 0xAC, 0x50, 0x7E, 0x94, 0x3C, 0x6D, 0xE6, 0x3F, 0xE1, 0x36, 0x82, 0x32, 0x25, + 0xD6, 0xFC, 0x73, 0xD8, 0x6D, 0x4C, 0x84, 0x39, 0x90, 0x13, 0xE0, 0x64, 0xE6, 0x68, 0x34, 0x92, 0x90, 0x7C, 0x7B, 0x78, 0xAE, 0xF2, 0xAA, 0xB1, 0x80, 0xDC, 0x33, 0xE5, 0xE6, 0xBD, 0xBD, 0x6D, + 0x49, 0x0E, 0x3A, 0xA8, 0xBE, 0x8E, 0x82, 0xFA, 0x6C, 0xB1, 0x3B, 0xEA, 0x36, 0x0C, 0x51, 0x0F, 0x9B, 0x4B, 0x5B, 0xA6, 0x64, 0x04, 0x27, 0xAD, 0xDD, 0xF3, 0xD6, 0x6D, 0xED, 0x41, 0xD1, 0xE2, + 0xA0, 0x61, 0x31, 0xE9, 0x50, 0x13, 0x68, 0x42, 0x73, 0x2C, 0x27, 0x34, 0x98, 0xD6, 0xA4, 0x7C, 0xED, 0x4E, 0xD1, 0x89, 0xB6, 0xE7, 0x39, 0x36, 0x1F, 0x68, 0xCC, 0xA0, 0xA9, 0x9D, 0x56, 0x02, + 0xB9, 0x76, 0x55, 0xAB, 0x26, 0x82, 0xE8, 0x37, 0xDB, 0xD6, 0x88, 0xC1, 0x73, 0xDD, 0x49, 0x50, 0xDD, 0x4C, 0xD4, 0xD3, 0xA3, 0x38, 0xF3, 0xFC, 0xFF, 0x8C, 0x71, 0x16, 0xEB, 0xC6, 0x30, 0xD0, + 0x5A, 0xFA, 0xB8, 0xDF, 0x7C, 0x75, 0x60, 0xF4, 0xDE, 0x9A, 0xD9, 0x22, 0x16, 0x26, 0x8E, 0xE1, 0x43, 0xA7, 0x22, 0xC0, 0x34, 0x97, 0xCE, 0x17, 0xEF, 0xE9, 0x8F, 0x67, 0x58, 0x0F, 0x0D, 0xDE, + 0xF5, 0x7F, 0x15, 0x25, 0x5E, 0x68, 0x85, 0x6D, 0x39, 0xA4, 0xEB, 0x33, 0x8A, 0x65, 0x33, 0x46, 0xFE, 0xDE, 0x46, 0x66, 0x3A, 0x62, 0x30, 0x7F, 0x65, 0x90, 0xE2, 0xEE, 0x7A, 0xB9, 0x28, 0xAC, + 0x5E, 0x8F, 0xA1, 0x63, 0xAA, 0x74, 0xE4, 0x02, 0x55, 0xD8, 0xD2, 0x41, 0x66, 0x8A, 0x1C, 0x71, 0x7E, 0x3F, 0x28, 0x99, 0x43, 0x50, 0xF4, 0x99, 0x08, 0xA3, 0x2E, 0x6F, 0xEC, 0x62, 0x06, 0xBD, + 0xF7, 0x93, 0x6D, 0xD2, 0xCF, 0x6A, 0x87, 0xB9, 0x99, 0x40, 0x45, 0x55, 0x2A, 0xCC, 0xE6, 0xEA, 0xF1, 0x29, 0x4E, 0x73, 0x27, 0xA1, 0x3E, 0x6E, 0xAC, 0x16, 0x22, 0x1A, 0x67, 0x6F, 0x60, 0x5D, + 0x6D, 0xA6, 0x36, 0x5D, 0x0D, 0xB0, 0x11, 0x35, 0x40, 0x50, 0x13, 0xF8, 0x74, 0x48, 0x1A, 0x68, 0x33, 0x04, 0x55, 0x28, 0x1A, 0x41, 0xE8, 0x3D, 0xF7, 0x6D, 0x20, 0xD1, 0xDF, 0x75, 0xDF, 0xEC, + 0xA0, 0x91, 0x7F, 0x3E, 0x94, 0xBE, 0xD2, 0x2D, 0x1E, 0xCE, 0xD8, 0xA9, 0xFC, 0x7B, 0x2A, 0x2E, 0x4A, 0x5B, 0x74, 0xD0, 0xB0, 0xC9, 0x28, 0x2B, 0xD6, 0x12, 0xA4, 0x86, 0x48, 0x99, 0x3F, 0x9F, + 0x01, 0x2B, 0xD7, 0x0A, 0x0E, 0x43, 0xDC, 0x3D, 0x1C, 0x0A, 0x16, 0x71, 0x1E, 0xBF, 0x6E, 0xA4, 0x79, 0xDB, 0x94, 0x1F, 0x68, 0xA6, 0x70, 0x1B, 0x57, 0xF7, 0xB8, 0x37, 0xB3, 0x0C, 0x0A, 0x6D, + 0x77, 0x11, 0x23, 0xD6, 0xFC, 0x70, 0xBD, 0xBE, 0x24, 0x44, 0x0C, 0xE4, 0xE2, 0x54, 0xA0, 0x70, 0x53, 0x4F, 0x1C, 0x18, 0x13, 0xC5, 0x16, 0x79, 0x12, 0x60, 0xA7, 0x36, 0x89, 0xDF, 0xE1, 0xBE, + 0xAD, 0x6E, 0xBF, 0x6A, 0xFF, 0x7E, 0xE4, 0x8D, 0xE1, 0xD5, 0x9C, 0x62, 0x22, 0x8B, 0x38, 0x3E, 0x0A, 0xCA, 0x06, 0x90, 0xF8, 0x05, 0xFE, 0xFD, 0xC5, 0x4F, 0xC4, 0xF9, 0x74, 0xBF, 0xAC, 0xCD, + 0xFE, 0x33, 0x21, 0x6C, 0xD2, 0xBC, 0x06, 0xBA, 0x7C, 0x2F, 0x55, 0xD7, 0xA0, 0x70, 0x8C, 0x48, 0x01, 0x4F, 0xF0, 0xC5, 0x35, 0xCD, 0x83, 0xD5, 0x47, 0x08, 0xFD, 0x70, 0x3E, 0x8E, 0xF5, 0x10, + 0xFA, 0x60, 0x72, 0xE2, 0x5F, 0xDA, 0xEB, 0x95, 0x33, 0xD4, 0x80, 0x60, 0x53, 0x07, 0x6C, 0xB8, 0xE4, 0xFE, 0x69, 0x46, 0xFD, 0x1A, 0x67, 0x0D, 0x1B, 0xDA, 0x92, 0x31, 0x1D, 0x5E, 0xD5, 0xFA, + 0x24, 0x5F, 0xA7, 0x4A, 0x6F, 0x04, 0xAE, 0x66, 0xE3, 0xC9, 0xE0, 0xA7, 0x18, 0x2C, 0xFD, 0xB2, 0x10, 0xE5, 0xA2, 0xF2, 0x8C, 0x95, 0x43, 0x99, 0x64, 0x74, 0x2A, 0x98, 0x7A, 0x16, 0x29, 0x85, + 0xDB, 0x91, 0xDF, 0x91, 0xD9, 0x52, 0x9D, 0x8B, 0x85, 0x0B, 0x86, 0x28, 0xA9, 0xC5, 0xC8, 0x45, 0x5B, 0xDB, 0x41, 0x7C, 0x92, 0x72, 0x24, 0xA9, 0xA8, 0xFF, 0xCD, 0xFE, 0x00, 0xC2, 0x28, 0xFA, + 0x28, 0x4C, 0x50, 0x52, 0x57, 0x70, 0x98, 0x15, 0x1E, 0x33, 0x78, 0x7F, 0x82, 0x87, 0xCB, 0x0D, 0x24, 0x31, 0x32, 0x45, 0x55, 0x84, 0x8A, 0x8D, 0x9C, 0xDF, 0xE3, 0xE4, 0xF0, 0xF1, 0x42, 0x61, + 0xD0, 0xFB, 0xFC, 0x02, 0x3C, 0x59, 0x6C, 0x74, 0x9E, 0xAE, 0xFB, 0x0A, 0x17, 0x84, 0xC8, 0xCF, 0xE5, 0xE7, 0x44, 0x8A, 0x98, 0x9F, 0xD8, 0xD9, 0x43, 0x66, 0xB4, 0xC7, 0xD6, 0xFF, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x0F, 0x1E, 0x23, 0x2B, 0x32, 0x38, 0x3E, + }, + }, + { + .name = "Dilithium Round 3, Level 5 (8-7) KAT 0", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_87, + .rho_len = 32, + .rho = { + 0x1C, 0x0E, 0xE1, 0x11, 0x1B, 0x08, 0x00, 0x3F, 0x28, 0xE6, 0x5E, 0x8B, 0x3B, 0xDE, 0xB0, 0x37, 0xCF, 0x8F, 0x22, 0x1D, 0xFC, 0xDA, 0xF5, 0x95, 0x0E, 0xDB, 0x38, 0xD5, 0x06, 0xD8, 0x5B, 0xEF, + }, + .seed_len = 32, + .seed = { + 0x39, 0x4D, 0x16, 0x95, 0x05, 0x9D, 0xFF, 0x40, 0xAE, 0x25, 0x6C, 0x5D, 0x5E, 0xDA, 0xBF, 0xB6, 0x9F, 0x5F, 0x40, 0xF3, 0x7A, 0x58, 0x8F, 0x50, 0x53, 0x2C, 0xA4, 0x08, 0xA8, 0x16, 0x8A, 0xB1, + }, + .tr_len = 32, + .tr = { + 0x85, 0xF6, 0x84, 0xAE, 0xB4, 0x01, 0xB9, 0xAA, 0xAF, 0x81, 0x2A, 0x00, 0xE1, 0x24, 0xFF, 0x56, 0xFE, 0xE5, 0x1B, 0xA7, 0xC1, 0x12, 0x82, 0x61, 0x7F, 0x05, 0x72, 0xCC, 0x79, 0x1D, 0xC8, 0x1C, + }, + .s1_len = 672, + .s1 = { + 0xC0, 0xA6, 0x71, 0x1A, 0x96, 0x6C, 0x11, 0x31, 0x2A, 0xD9, 0xA8, 0x21, 0xD8, 0x08, 0x65, 0x42, 0xA6, 0x00, 0xA4, 0xB4, 0x2C, 0x19, 0x40, 0x72, 0x02, 0x42, 0x62, 0x81, 0x06, 0x21, 0x0A, 0x43, + 0x85, 0x23, 0x31, 0x70, 0x93, 0x08, 0x10, 0x8B, 0x18, 0x8C, 0x02, 0x24, 0x92, 0xC1, 0xB2, 0x84, 0x12, 0xC4, 0x21, 0x8B, 0x04, 0x21, 0x81, 0xC8, 0x61, 0x02, 0x48, 0x05, 0x9C, 0x92, 0x01, 0xC0, + 0x34, 0x88, 0x19, 0x32, 0x6C, 0x58, 0x20, 0x46, 0x89, 0x18, 0x68, 0xA2, 0xC2, 0x8D, 0x82, 0x34, 0x6A, 0x1C, 0x09, 0x42, 0x00, 0xA2, 0x8C, 0xE3, 0xA6, 0x49, 0x1C, 0x11, 0x2C, 0xC2, 0x48, 0x12, + 0xE0, 0x90, 0x21, 0x91, 0x98, 0x50, 0x62, 0xC0, 0x84, 0x62, 0x24, 0x51, 0xCA, 0x06, 0x2C, 0x64, 0x24, 0x0E, 0x1B, 0xB3, 0x31, 0x24, 0x96, 0x85, 0x4B, 0x46, 0x06, 0xDB, 0x26, 0x68, 0xC3, 0x82, + 0x68, 0x44, 0x10, 0x46, 0xC9, 0xB6, 0x21, 0x14, 0x04, 0x81, 0x14, 0x45, 0x50, 0x24, 0x42, 0x08, 0x44, 0x22, 0x71, 0x0B, 0x92, 0x45, 0x9A, 0xA0, 0x81, 0x1A, 0x91, 0x70, 0x9C, 0x24, 0x10, 0x03, + 0x95, 0x70, 0x04, 0xC5, 0x04, 0xC8, 0x26, 0x92, 0xD2, 0x92, 0x00, 0xC0, 0xB2, 0x60, 0xC0, 0xA2, 0x68, 0x09, 0x19, 0x0A, 0xA2, 0x30, 0x0E, 0x18, 0x89, 0x69, 0xE0, 0x00, 0x8D, 0xD8, 0x48, 0x62, + 0xDA, 0x14, 0x71, 0x20, 0x18, 0x05, 0x19, 0x07, 0x44, 0x04, 0x12, 0x40, 0x9B, 0x12, 0x40, 0x11, 0x80, 0x10, 0xD1, 0x42, 0x81, 0x99, 0x28, 0x50, 0x8B, 0x10, 0x91, 0x02, 0x24, 0x64, 0xA0, 0x20, + 0x6D, 0x12, 0x46, 0x21, 0x1C, 0x83, 0x8C, 0x1B, 0x47, 0x69, 0x01, 0x06, 0x90, 0xCC, 0x06, 0x24, 0x81, 0x84, 0x69, 0x20, 0x98, 0x2C, 0x24, 0x12, 0x05, 0x21, 0xB1, 0x50, 0x41, 0x36, 0x02, 0x98, + 0x44, 0x6E, 0xD1, 0xA6, 0x31, 0x11, 0x05, 0x6A, 0xD3, 0xA8, 0x40, 0xCA, 0xA8, 0x4C, 0x62, 0xB0, 0x00, 0x03, 0x13, 0x4A, 0x53, 0x34, 0x46, 0x14, 0x19, 0x40, 0x04, 0xC5, 0x4C, 0xE3, 0x06, 0x69, + 0x5A, 0xB0, 0x89, 0x61, 0x16, 0x8E, 0xCB, 0x10, 0x80, 0x8B, 0x16, 0x8E, 0xD9, 0x90, 0x64, 0x0B, 0x94, 0x60, 0x24, 0x83, 0x85, 0x1A, 0xB3, 0x04, 0x54, 0x26, 0x22, 0x51, 0xB8, 0x25, 0x1C, 0x42, + 0x4A, 0x0B, 0x81, 0x48, 0x42, 0xC4, 0x44, 0x5A, 0x10, 0x20, 0x23, 0x80, 0x84, 0x09, 0xB7, 0x25, 0x4C, 0xC6, 0x48, 0x14, 0x85, 0x4D, 0x19, 0x38, 0x0E, 0x60, 0x16, 0x51, 0xD8, 0x32, 0x6A, 0x0A, + 0x91, 0x89, 0x08, 0xC1, 0x70, 0xE0, 0x96, 0x4D, 0x18, 0x46, 0x8C, 0x01, 0x32, 0x8D, 0x91, 0xC4, 0x05, 0x4A, 0x00, 0x61, 0x23, 0x08, 0x68, 0xA2, 0x10, 0x42, 0x10, 0xA8, 0x61, 0x13, 0x06, 0x21, + 0x8A, 0x24, 0x8E, 0x62, 0x06, 0x89, 0xC9, 0xB2, 0x45, 0x08, 0x27, 0x84, 0x51, 0x20, 0x0D, 0x98, 0x04, 0x66, 0xDC, 0x42, 0x05, 0x44, 0x24, 0x85, 0x24, 0x26, 0x28, 0x22, 0x21, 0x61, 0x20, 0x16, + 0x09, 0x0B, 0xA6, 0x2C, 0x0A, 0x11, 0x44, 0xE0, 0x92, 0x81, 0x58, 0x48, 0x0D, 0x42, 0x22, 0x10, 0xA0, 0x06, 0x09, 0x8B, 0x24, 0x6E, 0x81, 0x28, 0x8C, 0xC0, 0x24, 0x80, 0x90, 0x30, 0x8D, 0x84, + 0x36, 0x40, 0x4C, 0xA6, 0x84, 0x50, 0x04, 0x24, 0x94, 0xB6, 0x8D, 0xA2, 0x92, 0x6D, 0x18, 0xB3, 0x44, 0xA0, 0x00, 0x85, 0xE3, 0xB8, 0x05, 0x14, 0x05, 0x04, 0xA4, 0xC2, 0x90, 0x84, 0x22, 0x81, + 0xC3, 0x26, 0x2D, 0x0B, 0x20, 0x66, 0xCC, 0x90, 0x31, 0x98, 0x38, 0x28, 0x10, 0x16, 0x6C, 0xC1, 0x34, 0x45, 0xC0, 0x10, 0x22, 0x24, 0xC6, 0x88, 0x03, 0x46, 0x32, 0xD8, 0x40, 0x90, 0x1C, 0x20, + 0x68, 0x04, 0x15, 0x28, 0x9A, 0x18, 0x81, 0x44, 0x98, 0x8D, 0x9C, 0x20, 0x6E, 0x9C, 0x30, 0x2C, 0xC1, 0xB8, 0x20, 0x61, 0x42, 0x21, 0x08, 0x03, 0x10, 0xA0, 0xC2, 0x8C, 0x58, 0x12, 0x85, 0x53, + 0x20, 0x4C, 0x03, 0x30, 0x81, 0x4C, 0xA4, 0x8D, 0x44, 0xC0, 0x8D, 0x51, 0x40, 0x4C, 0x1C, 0xA7, 0x2C, 0x44, 0x08, 0x65, 0xA0, 0x38, 0x40, 0xDA, 0x20, 0x80, 0x81, 0x06, 0x85, 0x8C, 0x26, 0x0D, + 0xE2, 0xA8, 0x8C, 0x9C, 0x44, 0x11, 0x59, 0x42, 0x28, 0xC4, 0x26, 0x04, 0x44, 0x14, 0x26, 0xA1, 0x42, 0x64, 0x08, 0xC0, 0x85, 0x11, 0x01, 0x86, 0x9B, 0x48, 0x31, 0x99, 0xB2, 0x0C, 0x80, 0x46, + 0x44, 0x59, 0xA8, 0x8C, 0x00, 0x42, 0x08, 0x98, 0x82, 0x90, 0x0A, 0xB5, 0x45, 0x62, 0x24, 0x48, 0x12, 0x96, 0x05, 0x44, 0x12, 0x46, 0x00, 0xC8, 0x88, 0x13, 0xA0, 0x61, 0xE1, 0x28, 0x4D, 0x0A, + 0xB9, 0x91, 0x4B, 0x96, 0x20, 0x99, 0xB8, 0x44, 0x00, 0x31, 0x4E, 0x98, 0x12, 0x85, 0x00, 0xB6, 0x01, 0x83, 0xA0, 0x0D, 0x14, 0x15, 0x0E, 0x18, 0x81, 0x10, 0x19, 0x01, 0x22, 0x4A, 0x06, 0x68, + }, + .s2_len = 768, + .s2 = { + 0x1A, 0x49, 0x8D, 0xE1, 0xA2, 0x84, 0x11, 0xC6, 0x31, 0x21, 0x26, 0x25, 0x91, 0xA0, 0x6D, 0x03, 0x05, 0x24, 0xA1, 0xB6, 0x08, 0x94, 0x44, 0x72, 0x43, 0x34, 0x12, 0x5B, 0xB4, 0x20, 0x41, 0xB6, + 0x50, 0xD0, 0x88, 0x8D, 0x0B, 0x07, 0x4D, 0x1C, 0x94, 0x64, 0x4C, 0x20, 0x8E, 0x8B, 0x88, 0x08, 0xE0, 0x30, 0x09, 0x44, 0x20, 0x05, 0x49, 0x86, 0x4D, 0x03, 0x13, 0x4E, 0x19, 0xC9, 0x84, 0x09, + 0x37, 0x61, 0x1A, 0x43, 0x68, 0x4A, 0x80, 0x90, 0x02, 0x04, 0x31, 0x1C, 0x17, 0x42, 0x18, 0x40, 0x80, 0xC8, 0x30, 0x8E, 0xE1, 0xA2, 0x41, 0xC3, 0x34, 0x04, 0xA3, 0x28, 0x22, 0x51, 0x24, 0x71, + 0x82, 0x84, 0x01, 0x1B, 0xC0, 0x64, 0x23, 0x47, 0x72, 0x82, 0x14, 0x66, 0x5B, 0x38, 0x68, 0xE1, 0xC6, 0x29, 0x9B, 0x90, 0x40, 0x60, 0x38, 0x86, 0x83, 0xA0, 0x40, 0x84, 0x20, 0x04, 0x4C, 0x94, + 0x01, 0x10, 0x25, 0x8D, 0x82, 0x02, 0x4D, 0x9A, 0xB2, 0x69, 0x20, 0x15, 0x10, 0x60, 0x46, 0x2D, 0xC2, 0x14, 0x2E, 0x0C, 0xA8, 0x2C, 0x54, 0x16, 0x22, 0x03, 0x46, 0x89, 0x92, 0x06, 0x60, 0x08, + 0x07, 0x82, 0x0B, 0x47, 0x44, 0x48, 0x98, 0x09, 0x09, 0x43, 0x0E, 0xE4, 0x32, 0x0A, 0x1A, 0xC0, 0x65, 0xC0, 0xA4, 0x21, 0x44, 0xB2, 0x91, 0x58, 0xC6, 0x04, 0x11, 0x45, 0x20, 0xC4, 0xA4, 0x21, + 0x02, 0xA0, 0x70, 0x21, 0x22, 0x26, 0x23, 0xB2, 0x68, 0x4B, 0x08, 0x40, 0x01, 0x03, 0x91, 0x8B, 0x34, 0x81, 0x1A, 0x04, 0x04, 0x0C, 0xB0, 0x05, 0xC2, 0x92, 0x69, 0x90, 0x14, 0x68, 0x04, 0x46, + 0x49, 0x14, 0x83, 0x49, 0xA2, 0x34, 0x89, 0x19, 0xC7, 0x28, 0x94, 0x44, 0x71, 0x00, 0xC9, 0x49, 0x58, 0x38, 0x72, 0x02, 0x02, 0x90, 0x42, 0xC6, 0x4C, 0x0C, 0x17, 0x32, 0x48, 0xC6, 0x8C, 0x59, + 0x28, 0x31, 0x09, 0xB7, 0x28, 0xCB, 0x48, 0x0E, 0x9A, 0x22, 0x85, 0x1C, 0xB9, 0x11, 0xE3, 0xC6, 0x30, 0xC3, 0x48, 0x28, 0xCC, 0xB8, 0x28, 0x03, 0xC8, 0x08, 0xA4, 0xB6, 0x04, 0xD0, 0x18, 0x8C, + 0x60, 0x18, 0x72, 0xD0, 0x20, 0x92, 0x82, 0x02, 0x2E, 0x59, 0x18, 0x89, 0x08, 0x19, 0x32, 0xC9, 0x06, 0x52, 0x60, 0x90, 0x8C, 0x09, 0x80, 0x29, 0xA4, 0xB4, 0x8C, 0x8C, 0x34, 0x82, 0x08, 0x42, + 0x10, 0x02, 0x00, 0x08, 0x13, 0x01, 0x50, 0x83, 0xB6, 0x08, 0x41, 0x94, 0x4D, 0x1B, 0x49, 0x6C, 0x19, 0x39, 0x11, 0xCB, 0x32, 0x41, 0x02, 0xC0, 0x65, 0x48, 0x88, 0x91, 0x9B, 0x98, 0x61, 0x08, + 0xB5, 0x04, 0x49, 0xB4, 0x45, 0xD3, 0x30, 0x01, 0x98, 0x04, 0x6D, 0x53, 0x00, 0x89, 0x42, 0x32, 0x60, 0x8C, 0xB0, 0x90, 0x64, 0x88, 0x68, 0xD4, 0x32, 0x45, 0x48, 0x14, 0x71, 0x14, 0x98, 0x05, + 0x81, 0x00, 0x22, 0xDB, 0x44, 0x69, 0xD9, 0x24, 0x89, 0x11, 0x41, 0x12, 0x09, 0x19, 0x50, 0x92, 0xA0, 0x84, 0xC0, 0x34, 0x22, 0x4A, 0x24, 0x10, 0xDA, 0xC8, 0x09, 0xD2, 0xA8, 0x0D, 0x22, 0x85, + 0x21, 0x8B, 0xC8, 0x90, 0xC1, 0x00, 0x66, 0x5C, 0xC0, 0x25, 0x99, 0xA4, 0x61, 0x1A, 0xA4, 0x11, 0x0A, 0x24, 0x28, 0x5B, 0xC4, 0x48, 0x13, 0x14, 0x89, 0x63, 0x92, 0x61, 0x20, 0x30, 0x0C, 0x40, + 0x02, 0x25, 0x21, 0x88, 0x28, 0x24, 0x01, 0x8C, 0x10, 0x81, 0x6D, 0x4C, 0x42, 0x49, 0x01, 0x22, 0x2D, 0xC1, 0x96, 0x0C, 0x08, 0x48, 0x90, 0x01, 0xC1, 0x30, 0x23, 0xC1, 0x89, 0xA1, 0xC4, 0x64, + 0x12, 0x97, 0x09, 0xCC, 0x90, 0x91, 0x60, 0x20, 0x66, 0x1B, 0x96, 0x48, 0x82, 0xA8, 0x71, 0x91, 0xC0, 0x65, 0xDB, 0xC2, 0x01, 0x84, 0x36, 0x0A, 0x09, 0x24, 0x29, 0x52, 0x10, 0x4E, 0xDB, 0x24, + 0x0A, 0x61, 0x02, 0x10, 0x20, 0x38, 0x25, 0x98, 0x34, 0x60, 0x82, 0x24, 0x30, 0xC4, 0x12, 0x49, 0xC0, 0xA2, 0x05, 0x0C, 0x08, 0x85, 0x93, 0x28, 0x09, 0x63, 0xB2, 0x05, 0x23, 0x96, 0x20, 0x42, + 0x12, 0x0D, 0xD1, 0xC0, 0x10, 0x08, 0xC5, 0x40, 0xC1, 0x82, 0x65, 0x1B, 0x15, 0x92, 0xA4, 0x14, 0x51, 0x84, 0x04, 0x26, 0x53, 0x42, 0x52, 0x24, 0x23, 0x6D, 0x9C, 0x28, 0x4E, 0x50, 0x14, 0x05, + 0x8C, 0x20, 0x80, 0x24, 0x26, 0x65, 0x61, 0x44, 0x4C, 0x02, 0x11, 0x20, 0xC8, 0xC0, 0x4C, 0x18, 0xA0, 0x0D, 0x00, 0x38, 0x70, 0x99, 0x16, 0x12, 0xA1, 0x16, 0x40, 0xC4, 0x18, 0x45, 0x09, 0x93, + 0x88, 0x4C, 0x82, 0x21, 0xCB, 0xB2, 0x81, 0x21, 0x26, 0x61, 0xD1, 0xA8, 0x24, 0x41, 0x30, 0x84, 0x08, 0x80, 0x71, 0x00, 0xC6, 0x20, 0x52, 0x42, 0x92, 0x89, 0x24, 0x12, 0xA4, 0x26, 0x89, 0xE3, + 0xB0, 0x88, 0x21, 0x98, 0x8C, 0x11, 0x96, 0x2C, 0xE1, 0x96, 0x20, 0x51, 0xC2, 0x81, 0x20, 0x91, 0x80, 0x94, 0x16, 0x6E, 0x14, 0x94, 0x60, 0x20, 0xC9, 0x45, 0x9B, 0x22, 0x45, 0xA2, 0x38, 0x20, + 0xC0, 0x36, 0x08, 0x60, 0x90, 0x8D, 0x41, 0x06, 0x02, 0x5B, 0x06, 0x6E, 0xE1, 0x40, 0x0A, 0x89, 0x34, 0x6C, 0x1A, 0xB2, 0x69, 0xA4, 0x16, 0x10, 0x03, 0x33, 0x0E, 0x1A, 0x42, 0x28, 0x03, 0x19, + 0x6E, 0x11, 0x44, 0x84, 0x0B, 0x24, 0x4A, 0x1C, 0x16, 0x6A, 0x19, 0x98, 0x40, 0x03, 0xA2, 0x85, 0x41, 0xC0, 0x8C, 0xD2, 0x22, 0x61, 0x0C, 0x82, 0x10, 0x5A, 0xB0, 0x0D, 0x21, 0x14, 0x72, 0x5A, + 0x82, 0x80, 0x02, 0x86, 0x10, 0x0C, 0x27, 0x26, 0x5C, 0x48, 0x6E, 0xC9, 0x40, 0x6C, 0x1B, 0x49, 0x04, 0xE4, 0xB8, 0x49, 0xDB, 0x32, 0x8A, 0x9C, 0x24, 0x2C, 0x40, 0x38, 0x80, 0x22, 0xA9, 0x45, + }, + .t0_len = 3328, + .t0 = { + 0x12, 0x29, 0xA4, 0xE6, 0x5E, 0xD3, 0x1C, 0x79, 0x3E, 0xCB, 0x5B, 0x89, 0xC5, 0x5D, 0xC3, 0x33, 0xA2, 0x77, 0xBF, 0x5C, 0x41, 0x28, 0xA2, 0x14, 0x01, 0xAF, 0xA8, 0xD4, 0x28, 0xC8, 0x21, 0xE9, + 0x7A, 0xEA, 0x05, 0xB3, 0xAD, 0x29, 0x23, 0xBD, 0x97, 0x10, 0x87, 0x1C, 0xE8, 0xB3, 0xB1, 0x1A, 0x71, 0x1C, 0x9A, 0xAC, 0xBA, 0x10, 0x8C, 0xAF, 0x43, 0xA1, 0x72, 0xD6, 0x59, 0x94, 0x01, 0xDB, + 0x89, 0x68, 0x1D, 0x0B, 0x87, 0x4E, 0xC3, 0x57, 0xA5, 0x29, 0x5C, 0x0A, 0x08, 0xD5, 0x89, 0xC4, 0x53, 0x9F, 0x9C, 0x59, 0xF3, 0x3F, 0x06, 0x44, 0x64, 0x41, 0x20, 0x49, 0x84, 0xE1, 0xF9, 0x87, + 0x3C, 0x1F, 0x97, 0x75, 0xB9, 0x7E, 0xD4, 0x00, 0xC9, 0x98, 0xB0, 0x51, 0x62, 0xB6, 0x18, 0x98, 0x61, 0xF2, 0x8D, 0xAE, 0x36, 0xC2, 0x13, 0x37, 0x65, 0x71, 0x11, 0x76, 0xCA, 0xAF, 0x5A, 0x1D, + 0xCB, 0x2A, 0x0E, 0x22, 0x3A, 0x5F, 0x07, 0x9B, 0x07, 0x41, 0xA5, 0xE6, 0xD5, 0x10, 0xE5, 0x87, 0x32, 0xDC, 0x03, 0x59, 0xD7, 0x9A, 0x77, 0x41, 0xA3, 0x79, 0x1C, 0xA6, 0x50, 0x4F, 0x07, 0xCA, + 0x8A, 0x2C, 0x03, 0x12, 0x71, 0x18, 0x45, 0x20, 0xEB, 0x76, 0xA0, 0x0B, 0x9B, 0x46, 0x26, 0xDB, 0x37, 0x34, 0x1C, 0x71, 0x80, 0x65, 0xED, 0x95, 0xFE, 0x4C, 0xB0, 0x54, 0xBF, 0xE7, 0x1E, 0x80, + 0x26, 0x0D, 0x21, 0x90, 0x7B, 0x9B, 0xFA, 0xEC, 0x86, 0xAC, 0x83, 0xA4, 0x85, 0x63, 0xC0, 0xB9, 0xB2, 0xEF, 0x4B, 0x9B, 0x4E, 0xCB, 0xCB, 0x2F, 0x12, 0x91, 0x98, 0x4E, 0x89, 0xE8, 0x4C, 0x55, + 0x69, 0x06, 0x47, 0xE2, 0x65, 0x47, 0xD7, 0x3E, 0x4C, 0xB7, 0xF0, 0xE0, 0x6E, 0xFF, 0xC3, 0xC4, 0x79, 0xE2, 0x56, 0x8E, 0x74, 0x64, 0xEA, 0xBF, 0x1D, 0x1C, 0x4E, 0xFE, 0x21, 0x11, 0x12, 0xE6, + 0x2B, 0xEA, 0x8B, 0x85, 0x5F, 0x50, 0xD7, 0x16, 0x51, 0x32, 0x9C, 0x00, 0xEF, 0x61, 0x9F, 0x53, 0x7E, 0x45, 0x4B, 0x09, 0x5A, 0x9D, 0xF6, 0xA8, 0x59, 0x0E, 0x5B, 0xBA, 0xA1, 0x5C, 0x9E, 0x64, + 0xE7, 0x01, 0xE3, 0x74, 0x69, 0x74, 0x94, 0x62, 0xA2, 0x11, 0x95, 0x41, 0xE7, 0x55, 0x49, 0xD0, 0x56, 0xA2, 0x5B, 0xBC, 0xEE, 0x11, 0xCD, 0x9F, 0xC6, 0x72, 0x42, 0x2A, 0xD2, 0xAE, 0x97, 0x91, + 0x3D, 0x30, 0xBE, 0x3C, 0xD8, 0x5F, 0x58, 0xCF, 0xA9, 0x04, 0xF4, 0x43, 0xAC, 0x3A, 0x8D, 0xFD, 0xBC, 0x2C, 0xC9, 0xC8, 0xC3, 0x9B, 0x24, 0x4E, 0xE7, 0xE0, 0xD9, 0x5B, 0xEC, 0x69, 0x27, 0xA2, + 0xB0, 0xB9, 0x4E, 0x97, 0x3F, 0x98, 0x12, 0x24, 0x46, 0x43, 0x14, 0x6E, 0x19, 0x01, 0x3B, 0x7F, 0xE1, 0x71, 0x14, 0xA0, 0xF3, 0x9F, 0x92, 0x28, 0x6B, 0xE0, 0xF0, 0xEE, 0x39, 0x6F, 0xB7, 0x4C, + 0x76, 0xC9, 0x10, 0x04, 0xB8, 0x27, 0xD2, 0x18, 0x95, 0x1C, 0x77, 0xBD, 0xB8, 0x15, 0x90, 0xAE, 0xDF, 0xEA, 0x9E, 0x62, 0xBE, 0x0F, 0x22, 0xAF, 0xF5, 0x5E, 0x36, 0xAB, 0x57, 0x2D, 0xF1, 0x3A, + 0xB9, 0xF5, 0xEA, 0xFC, 0xBC, 0x34, 0xDF, 0x26, 0x6F, 0xE1, 0x60, 0xC6, 0xB6, 0x35, 0xB0, 0xC3, 0xB6, 0x3C, 0x89, 0x29, 0x20, 0x18, 0x5F, 0x11, 0x2B, 0x96, 0x99, 0x8B, 0x5B, 0x5B, 0xB9, 0x73, + 0xB3, 0x90, 0x08, 0xB2, 0xF0, 0x43, 0x40, 0x35, 0xD4, 0x3B, 0xD2, 0xE4, 0x9F, 0x2C, 0x17, 0x45, 0x20, 0xD3, 0xA8, 0x98, 0x54, 0xCD, 0x82, 0x50, 0xD6, 0x20, 0x0A, 0x1E, 0xB5, 0x10, 0x79, 0x22, + 0x46, 0x56, 0xD0, 0xB3, 0x34, 0xCE, 0xE3, 0x43, 0x0B, 0x87, 0xE1, 0xFF, 0x90, 0x4D, 0x10, 0x34, 0xC2, 0xD8, 0xA7, 0x04, 0x7B, 0x2D, 0x22, 0x56, 0x33, 0x19, 0x04, 0x10, 0x01, 0x2C, 0x16, 0x1C, + 0x76, 0x8C, 0x1F, 0xF8, 0xFC, 0x17, 0x9A, 0x44, 0x68, 0x64, 0xDF, 0x93, 0xE0, 0x9D, 0x1E, 0x6C, 0x29, 0x48, 0x7C, 0xAB, 0x04, 0x4E, 0xF8, 0x68, 0xD4, 0x31, 0xB1, 0x76, 0x31, 0x84, 0xAD, 0xCB, + 0x39, 0x51, 0x6D, 0xD1, 0x27, 0x6B, 0xD8, 0x41, 0xEC, 0x49, 0x2A, 0x84, 0x51, 0x77, 0x4E, 0xDA, 0x10, 0x6E, 0x73, 0x21, 0xED, 0x5A, 0x62, 0x25, 0xC3, 0x53, 0x24, 0xC5, 0x10, 0x66, 0x3B, 0x9B, + 0xEA, 0x05, 0xF1, 0xDB, 0xC8, 0xD5, 0xDB, 0x69, 0xA7, 0x7E, 0xCE, 0x3E, 0x42, 0x65, 0xC5, 0xE8, 0x10, 0x69, 0x86, 0x45, 0x80, 0xB5, 0x28, 0xCC, 0x2C, 0xBB, 0xFB, 0xDE, 0x62, 0x5A, 0xF2, 0xC1, + 0xC5, 0xCB, 0x06, 0xDD, 0x80, 0x58, 0x54, 0x04, 0x96, 0x4D, 0x21, 0x11, 0x4B, 0x8B, 0x13, 0xCA, 0xFB, 0x6D, 0xBE, 0x1B, 0x42, 0x8E, 0xBC, 0x87, 0x17, 0xCC, 0xD1, 0x1B, 0xFB, 0x34, 0x72, 0x60, + 0xAA, 0x70, 0x1B, 0xF2, 0x28, 0x35, 0xB3, 0xF1, 0x06, 0x2E, 0xAD, 0x36, 0xAC, 0xB9, 0x6D, 0x74, 0x96, 0xF7, 0x2A, 0xA5, 0xFF, 0x1A, 0x13, 0x04, 0xBC, 0x02, 0xE3, 0x58, 0xE6, 0x0B, 0x1C, 0x82, + 0x30, 0xBF, 0x8F, 0xFA, 0xFD, 0x36, 0xE0, 0xF6, 0xB2, 0xE3, 0xD8, 0x58, 0x2F, 0xD3, 0xA4, 0x38, 0x11, 0xAC, 0x24, 0xD0, 0x60, 0x08, 0x10, 0x35, 0x42, 0x87, 0x8C, 0xB5, 0xCE, 0x99, 0xF8, 0x92, + 0x0C, 0xC8, 0x02, 0xDA, 0x4E, 0xD2, 0x18, 0x39, 0x56, 0x83, 0x4D, 0xA4, 0xC7, 0x19, 0x55, 0x0D, 0xB2, 0x47, 0x95, 0xAC, 0xE0, 0x9D, 0x88, 0xCA, 0x30, 0x43, 0xAF, 0xCC, 0xC9, 0xAB, 0x0F, 0x03, + 0x06, 0x67, 0x1F, 0xD1, 0xF2, 0x50, 0x95, 0x7C, 0xC6, 0x24, 0x64, 0xC9, 0xEA, 0x5E, 0x44, 0x4C, 0x6E, 0xB4, 0x76, 0xD0, 0x92, 0x46, 0x56, 0x08, 0xFE, 0xB6, 0xB7, 0xD5, 0x39, 0x8A, 0x02, 0x9E, + 0x1E, 0xEA, 0xE5, 0x0D, 0xB5, 0xF9, 0xF9, 0x95, 0x50, 0xA9, 0x66, 0x83, 0x43, 0xEF, 0x29, 0x70, 0xF2, 0x25, 0x31, 0x67, 0x8E, 0x36, 0x71, 0x3B, 0x81, 0xCB, 0x36, 0x33, 0xF1, 0xDD, 0xD4, 0x67, + 0x69, 0x82, 0x6E, 0x43, 0x60, 0xDE, 0x19, 0xA5, 0x63, 0x18, 0xD9, 0xEB, 0x59, 0xF9, 0x7A, 0x9B, 0x3E, 0xD2, 0x2B, 0xFD, 0x89, 0x50, 0x11, 0x26, 0x29, 0x5E, 0x89, 0xFC, 0x73, 0x5C, 0x36, 0x19, + 0xD7, 0x7F, 0x6F, 0xB9, 0x35, 0xC2, 0xFB, 0x46, 0xED, 0xD0, 0xA4, 0xD2, 0x92, 0x17, 0x77, 0xB0, 0xEF, 0xCD, 0x58, 0xBE, 0xDC, 0xEB, 0x9E, 0xA5, 0x66, 0x6B, 0x18, 0xDF, 0xAC, 0xF9, 0xBF, 0x76, + 0x33, 0x3C, 0x5E, 0xDA, 0xC7, 0x2B, 0x04, 0xE6, 0x57, 0xE4, 0xE0, 0x86, 0x5E, 0x04, 0x3A, 0x64, 0x68, 0xC5, 0xE6, 0x9D, 0x5B, 0xCB, 0xE5, 0x84, 0x2B, 0xF4, 0x5B, 0xEE, 0x77, 0x91, 0x5F, 0x05, + 0x71, 0xD1, 0x50, 0xD6, 0x06, 0xA6, 0xF2, 0xAC, 0x37, 0x37, 0x92, 0x90, 0x88, 0x91, 0xBA, 0x85, 0xF4, 0x5C, 0xB4, 0x09, 0xD9, 0x63, 0xE4, 0x9B, 0x5B, 0x96, 0x97, 0x8A, 0x19, 0x39, 0x16, 0x0A, + 0x8D, 0xB9, 0xD6, 0x3C, 0x4E, 0xA0, 0xD6, 0xA7, 0xD0, 0x93, 0x70, 0xAC, 0x1C, 0x24, 0x49, 0x8D, 0x21, 0xA8, 0xD5, 0xB7, 0x64, 0xA3, 0x9A, 0x41, 0x2E, 0x5B, 0x54, 0xBD, 0x1C, 0x96, 0x4D, 0x24, + 0x4A, 0x45, 0x55, 0x64, 0x5F, 0x1F, 0x90, 0x53, 0xF8, 0xBB, 0x33, 0xF6, 0xF7, 0x51, 0x46, 0x80, 0x7B, 0x4E, 0x9E, 0x07, 0xB2, 0x3C, 0x98, 0x06, 0xFF, 0x75, 0x72, 0x46, 0x9C, 0x09, 0x43, 0x99, + 0xBA, 0x97, 0x79, 0xB9, 0x62, 0xB4, 0xC8, 0xA9, 0x57, 0xF8, 0x69, 0x91, 0x1E, 0xB1, 0x3F, 0x14, 0x02, 0x24, 0xAC, 0x4E, 0xE7, 0x62, 0x01, 0xC0, 0x2F, 0x24, 0xC7, 0xED, 0xC3, 0xA9, 0x80, 0x89, + 0x9A, 0x30, 0xBA, 0xD2, 0xB1, 0x2D, 0x57, 0x28, 0xF0, 0x97, 0x17, 0x6D, 0x00, 0x17, 0xF3, 0x47, 0x3D, 0x2F, 0xBB, 0xD4, 0x3C, 0xC2, 0x3A, 0x50, 0x1E, 0x81, 0xE3, 0x81, 0xBE, 0x01, 0x79, 0xBF, + 0x68, 0xCA, 0x50, 0xFD, 0x23, 0x55, 0xCA, 0x7B, 0x64, 0xF5, 0x3E, 0x0C, 0x7D, 0x5B, 0xCA, 0x4E, 0x7B, 0xE6, 0x91, 0x63, 0xE3, 0x16, 0xFE, 0xBB, 0x49, 0xA9, 0x34, 0x0F, 0x15, 0x7B, 0xAC, 0x3B, + 0x0B, 0xD8, 0x4A, 0x3B, 0x02, 0x7A, 0x2F, 0xE4, 0x4E, 0xC2, 0x66, 0xA8, 0xCE, 0x4A, 0x17, 0x1B, 0x91, 0x82, 0x8F, 0x45, 0x43, 0x02, 0xAA, 0x9B, 0x66, 0x49, 0x67, 0xE6, 0x7D, 0xB3, 0x8A, 0xA4, + 0xE3, 0xBC, 0x35, 0x3D, 0x15, 0x18, 0xA7, 0xFE, 0xC1, 0x18, 0x8B, 0x7D, 0x5B, 0x7E, 0x19, 0x52, 0x1F, 0x1A, 0x28, 0x77, 0x00, 0x69, 0x89, 0xB0, 0xFE, 0x91, 0x89, 0x46, 0xB7, 0x59, 0x3E, 0xD1, + 0x51, 0x20, 0xBF, 0x7D, 0x23, 0xF9, 0x92, 0x10, 0xDD, 0xB7, 0x6D, 0xAF, 0x86, 0xE2, 0x37, 0xB2, 0x37, 0x9C, 0xA1, 0x2E, 0x55, 0x63, 0x6C, 0x83, 0x40, 0x8E, 0x6D, 0x2B, 0x35, 0x85, 0xFA, 0xBC, + 0xBC, 0x0F, 0x6C, 0x48, 0x76, 0x7E, 0x36, 0x3A, 0xC8, 0x47, 0xCC, 0xC6, 0x7E, 0xB7, 0xC9, 0x37, 0xBB, 0xD9, 0x41, 0x10, 0x0D, 0x78, 0x77, 0x4A, 0xE1, 0xF4, 0x43, 0x39, 0xDC, 0xDC, 0xB0, 0xE7, + 0x00, 0xAC, 0x10, 0x8D, 0xAA, 0x92, 0xCD, 0x9E, 0xA1, 0x9F, 0x82, 0x38, 0xF2, 0x86, 0x76, 0xFE, 0xE7, 0xBD, 0x1B, 0x9F, 0x37, 0xA6, 0xCA, 0x17, 0xD7, 0xCF, 0x40, 0x42, 0xFE, 0x39, 0xDD, 0x93, + 0x77, 0x82, 0x6C, 0x4C, 0xAB, 0x29, 0x32, 0xE1, 0x2D, 0xE5, 0x3B, 0x08, 0x1A, 0x6C, 0x25, 0xC0, 0xF4, 0x7D, 0xA3, 0xD9, 0x16, 0x83, 0x1E, 0x42, 0x47, 0xD0, 0x97, 0x81, 0x1E, 0x1A, 0x08, 0x70, + 0xCB, 0x61, 0xF4, 0xAC, 0xA1, 0x27, 0xEA, 0xF8, 0x5A, 0x9C, 0xA6, 0x66, 0xFA, 0x6C, 0x36, 0x39, 0x8F, 0x0E, 0x74, 0x20, 0xCA, 0x98, 0x95, 0xC6, 0x3A, 0x1A, 0xC4, 0xDB, 0x49, 0xA1, 0xD7, 0x5F, + 0x56, 0x46, 0x4C, 0x1E, 0x0C, 0xF9, 0x28, 0x3A, 0x45, 0x44, 0x56, 0x50, 0xF9, 0x5F, 0xAD, 0xF6, 0xC8, 0x8D, 0xB3, 0xCE, 0x7C, 0x0E, 0x5D, 0x0E, 0x72, 0x61, 0xE8, 0x04, 0xC0, 0x3A, 0x41, 0x9E, + 0x4C, 0xC2, 0x50, 0x10, 0x99, 0xCA, 0x53, 0x63, 0x44, 0x60, 0x7B, 0x07, 0xE8, 0x25, 0x32, 0x3A, 0xD3, 0x0B, 0xE7, 0x5F, 0x84, 0xE6, 0xC5, 0xBE, 0x23, 0x8E, 0xC7, 0x86, 0x17, 0xA0, 0xA2, 0x34, + 0x14, 0xC7, 0xF8, 0xCD, 0x60, 0x91, 0x30, 0x31, 0xBC, 0x93, 0x01, 0x78, 0x6D, 0x5C, 0x19, 0xD9, 0x30, 0xB5, 0x06, 0xC4, 0x95, 0x98, 0x32, 0x23, 0xEC, 0x1B, 0xF7, 0x87, 0xC3, 0x3D, 0x22, 0x8A, + 0x11, 0x0E, 0x57, 0x42, 0x87, 0x73, 0xE3, 0x4F, 0x12, 0x66, 0x3D, 0x11, 0xC1, 0x55, 0xDF, 0xCE, 0x38, 0x0D, 0x65, 0x76, 0x4C, 0x26, 0x59, 0xEA, 0xA0, 0xA1, 0xA2, 0xE7, 0x64, 0xEB, 0xB5, 0xA9, + 0xE5, 0xA7, 0x19, 0x2E, 0x90, 0x86, 0xA6, 0xDE, 0x4A, 0x38, 0xFC, 0xFD, 0x04, 0x12, 0x42, 0x42, 0x60, 0x62, 0x0C, 0x1E, 0x56, 0x7A, 0x2D, 0x8B, 0x1A, 0xF3, 0x55, 0x48, 0x19, 0xA0, 0x0D, 0x5C, + 0x7E, 0x56, 0x66, 0xD0, 0xE6, 0x56, 0xF8, 0xD4, 0x5C, 0x67, 0xC5, 0x44, 0x8D, 0xAB, 0x5E, 0xB6, 0xE6, 0x02, 0x93, 0x79, 0xC4, 0x7A, 0x24, 0xD0, 0x11, 0xF5, 0x6E, 0x5F, 0xAA, 0x49, 0xFC, 0x6B, + 0xB2, 0xD7, 0x50, 0xED, 0x4C, 0x95, 0xF8, 0x35, 0x38, 0x4F, 0x2F, 0xAA, 0xB1, 0x3C, 0x1C, 0xCA, 0x71, 0xA1, 0xEB, 0xD2, 0x29, 0x9E, 0x96, 0x32, 0xE5, 0x29, 0xCE, 0x77, 0x14, 0x9F, 0x5F, 0xAC, + 0x31, 0xAB, 0x28, 0xDC, 0xC7, 0x06, 0x70, 0xBB, 0xAB, 0x9F, 0x7B, 0x6F, 0xFE, 0xAA, 0xBC, 0x7D, 0xC4, 0x51, 0x3D, 0x8F, 0xAC, 0x4B, 0xCF, 0x7E, 0x5E, 0x72, 0x97, 0xDB, 0x69, 0xE4, 0xB6, 0x25, + 0x38, 0xF9, 0xCA, 0xBD, 0x90, 0x2B, 0x10, 0x07, 0xE3, 0xBA, 0xF6, 0x7F, 0x94, 0x3D, 0xFD, 0xC6, 0xAA, 0x75, 0x62, 0xFA, 0xBB, 0x1E, 0x8F, 0xAC, 0xF8, 0x11, 0xC7, 0x63, 0x35, 0x79, 0x0A, 0x16, + 0xF2, 0x1E, 0xCB, 0x72, 0xFC, 0x1B, 0xA9, 0x42, 0x76, 0xB2, 0x09, 0x80, 0x7E, 0xA5, 0x2E, 0x74, 0xF2, 0xB6, 0xCA, 0x0B, 0x3F, 0xDC, 0x30, 0x50, 0x1F, 0x63, 0x10, 0xEC, 0x99, 0x55, 0xB0, 0x51, + 0x81, 0x8D, 0xAE, 0x10, 0x80, 0xFD, 0x4D, 0xD2, 0x4C, 0x72, 0x2D, 0x68, 0xDE, 0x33, 0xEA, 0x76, 0x9B, 0x4E, 0x63, 0x70, 0x07, 0xCF, 0xDC, 0xE1, 0x80, 0x4A, 0xC2, 0xA7, 0x71, 0xF8, 0x8F, 0x59, + 0xBA, 0xCE, 0xDB, 0x4D, 0xFB, 0x79, 0xA4, 0x1E, 0xA7, 0x0F, 0x14, 0xAC, 0xCE, 0x6A, 0x5A, 0x8A, 0x88, 0x43, 0xB5, 0x95, 0x89, 0xE4, 0x52, 0x8B, 0xA8, 0x52, 0x10, 0x42, 0x1D, 0x1E, 0x59, 0x5F, + 0x84, 0xC2, 0x75, 0x90, 0x47, 0xDB, 0x47, 0x22, 0x26, 0x73, 0x86, 0x8C, 0x00, 0x27, 0xEE, 0xFD, 0x99, 0x6E, 0xF8, 0xC8, 0xC4, 0xF3, 0x67, 0xA9, 0x1D, 0xEC, 0xF1, 0x79, 0x43, 0x22, 0x7D, 0x4D, + 0x00, 0x44, 0x7F, 0xFC, 0x6C, 0xC8, 0x66, 0x5E, 0x08, 0xD2, 0x93, 0xA4, 0xDE, 0x4E, 0xE1, 0x15, 0x69, 0xB9, 0x5B, 0xB4, 0xDA, 0xE7, 0x58, 0x15, 0x0E, 0x55, 0x78, 0x32, 0x55, 0xE2, 0xF3, 0x22, + 0x27, 0xB4, 0x5A, 0x9D, 0x26, 0x19, 0x77, 0x1C, 0xED, 0x51, 0x2D, 0x5C, 0xD8, 0x90, 0x18, 0xC9, 0x9E, 0x2F, 0x05, 0x23, 0x3E, 0xF5, 0x86, 0x0F, 0xEC, 0xB3, 0x79, 0x1B, 0x53, 0xAD, 0x2C, 0x22, + 0x8A, 0xBA, 0xBB, 0x9F, 0xD1, 0xF5, 0x04, 0x38, 0xE9, 0xB0, 0xC6, 0xEA, 0x61, 0xE2, 0x0B, 0xB5, 0xAC, 0x0A, 0xAD, 0x30, 0x50, 0x9F, 0xEA, 0x9A, 0x44, 0x1D, 0x55, 0x5C, 0xDD, 0x34, 0x50, 0x9C, + 0xFC, 0x60, 0x62, 0xE6, 0xB8, 0x1D, 0xCA, 0xCF, 0xD5, 0xF5, 0xC9, 0xC5, 0x26, 0xB3, 0x8D, 0x70, 0x4C, 0x1F, 0x0F, 0x28, 0xB4, 0xFB, 0x7C, 0x1A, 0xC6, 0x9A, 0xA1, 0x96, 0xCF, 0x81, 0x2E, 0x44, + 0x46, 0xEF, 0x68, 0x02, 0x87, 0x44, 0xD2, 0xA5, 0x40, 0xFA, 0x7A, 0x69, 0xCF, 0x87, 0xA1, 0xF9, 0x68, 0x24, 0xE4, 0xC6, 0x87, 0x82, 0x35, 0xF0, 0xCC, 0xA3, 0xE9, 0x7B, 0x2B, 0x22, 0xB0, 0x93, + 0xD9, 0x5E, 0xE1, 0x8D, 0xBF, 0xE6, 0x76, 0x1D, 0xFA, 0xF8, 0x34, 0x47, 0x51, 0x86, 0x07, 0x56, 0x02, 0x31, 0x3E, 0xE2, 0xA2, 0x99, 0xBC, 0xCC, 0xC6, 0x53, 0x1E, 0xDA, 0x54, 0x10, 0xCC, 0xFA, + 0x09, 0xEC, 0xB8, 0xA6, 0x0D, 0x28, 0x33, 0x7A, 0xA5, 0x56, 0x58, 0x6D, 0x78, 0x48, 0x49, 0x38, 0x0F, 0x02, 0xEB, 0xB8, 0x37, 0xCB, 0x0B, 0xDE, 0x57, 0xBB, 0xA9, 0x07, 0xB6, 0x7C, 0x7A, 0xD8, + 0x66, 0xE1, 0xDD, 0xB1, 0xC7, 0x9D, 0x96, 0x1D, 0x70, 0xF5, 0x5D, 0x05, 0x9A, 0xCF, 0xD3, 0x9F, 0x5B, 0xD3, 0x03, 0x74, 0xB4, 0x84, 0x5E, 0x04, 0xEC, 0x26, 0xE8, 0xB5, 0xB9, 0x3F, 0xC4, 0x54, + 0x4F, 0x24, 0xAE, 0x99, 0xC9, 0xE5, 0x1E, 0x43, 0x57, 0x75, 0xD2, 0x20, 0x80, 0xE1, 0x9E, 0x3A, 0xC2, 0x25, 0xC7, 0xE1, 0xEE, 0x0A, 0x56, 0xB9, 0x52, 0x30, 0x7F, 0x44, 0xBA, 0xCF, 0x4C, 0x87, + 0x85, 0x35, 0x5C, 0x09, 0xDB, 0xD0, 0xD8, 0x60, 0x57, 0xF0, 0xA6, 0xA9, 0x88, 0xC3, 0x65, 0x74, 0x20, 0x25, 0x19, 0xDE, 0xBA, 0x04, 0x56, 0x98, 0xD7, 0x24, 0x27, 0x77, 0x0C, 0x37, 0x31, 0xC9, + 0xB7, 0x53, 0x5F, 0xAA, 0xF0, 0xCC, 0xA9, 0xD1, 0x3C, 0x42, 0x12, 0xB7, 0x62, 0x94, 0x57, 0x52, 0xE7, 0xA6, 0x53, 0x9B, 0x47, 0xBE, 0xA9, 0x66, 0x48, 0x23, 0x18, 0xA9, 0xCF, 0xE3, 0xBA, 0xEC, + 0x6A, 0x83, 0xFB, 0x34, 0xF0, 0xB6, 0x8E, 0xE9, 0x77, 0x97, 0x42, 0x0F, 0xAD, 0xC3, 0xF0, 0x25, 0xEE, 0x9F, 0x18, 0xBE, 0xA3, 0x8F, 0xBE, 0xC0, 0xC5, 0xDE, 0xAA, 0xC7, 0xA5, 0x2F, 0x7E, 0xB8, + 0xD9, 0x4F, 0xE4, 0xC6, 0x62, 0x54, 0x14, 0x57, 0xA1, 0x53, 0x82, 0x4B, 0xE6, 0x0D, 0x7D, 0xB8, 0x33, 0x89, 0x0F, 0x3A, 0xC3, 0xF7, 0xBD, 0x6D, 0x73, 0xF8, 0x0C, 0x67, 0x2B, 0x76, 0xA5, 0x26, + 0x7D, 0xF2, 0x2C, 0xFB, 0x5E, 0x1B, 0x92, 0xB0, 0xCD, 0x68, 0xE9, 0xA9, 0x20, 0x92, 0x43, 0xA4, 0x2A, 0x30, 0xF7, 0xAA, 0x1F, 0x03, 0xD0, 0xD9, 0x11, 0x3F, 0x04, 0xB7, 0x6E, 0xB5, 0xAA, 0x69, + 0xBC, 0x9B, 0x8F, 0xE7, 0x98, 0xE7, 0x75, 0x01, 0xB0, 0x56, 0x30, 0x29, 0xF5, 0x02, 0xF7, 0x79, 0x4D, 0xD3, 0x90, 0x74, 0x7A, 0xED, 0x08, 0x5C, 0x22, 0xB2, 0x16, 0x11, 0xA9, 0xC7, 0x62, 0x38, + 0xEF, 0x65, 0x84, 0xAE, 0xFB, 0xB3, 0x57, 0xF8, 0x36, 0x25, 0x86, 0xC5, 0x9F, 0xCA, 0x8E, 0x09, 0x26, 0x10, 0x11, 0x5F, 0x4D, 0xC2, 0x93, 0x0D, 0x72, 0x24, 0x28, 0x5E, 0xB8, 0xFD, 0x99, 0x2F, + 0x82, 0x17, 0xAE, 0x94, 0x70, 0xA7, 0x4A, 0xE3, 0xE8, 0x06, 0x01, 0x0C, 0x8D, 0x02, 0x19, 0x48, 0xBE, 0x57, 0xAB, 0x1D, 0x62, 0xC0, 0x41, 0x2E, 0xA5, 0xC9, 0x69, 0xD0, 0x56, 0x68, 0x41, 0xF2, + 0xE2, 0x56, 0x8E, 0x01, 0x33, 0x64, 0xD8, 0x7C, 0xAF, 0x33, 0x22, 0x9D, 0x2A, 0xA6, 0xC5, 0x6B, 0x9F, 0xB4, 0xC1, 0x36, 0xA1, 0x3F, 0x5E, 0x73, 0x3A, 0x91, 0xEF, 0xF2, 0x1D, 0xCB, 0x29, 0x0D, + 0x8E, 0xC6, 0xDC, 0x0A, 0x50, 0xE5, 0x7C, 0x1F, 0x65, 0xEB, 0x2B, 0xA1, 0xC3, 0x9D, 0xDB, 0x1C, 0x09, 0x54, 0x24, 0xE6, 0xF4, 0x1F, 0x9E, 0x86, 0x56, 0x7F, 0x91, 0x14, 0x00, 0xD8, 0x5C, 0x90, + 0xD6, 0x4F, 0xC7, 0xE6, 0xEC, 0xC2, 0x88, 0x04, 0xF2, 0x70, 0x42, 0x40, 0x24, 0x9E, 0xFC, 0x8F, 0xEC, 0x69, 0xE3, 0x66, 0xF3, 0x68, 0x7A, 0x76, 0x20, 0x5C, 0x0D, 0x1D, 0xD6, 0x48, 0x39, 0x12, + 0xA8, 0xF6, 0x8E, 0xAE, 0x2C, 0xB3, 0x52, 0x0A, 0x8B, 0x17, 0x2C, 0xF2, 0xCD, 0x2B, 0x03, 0x80, 0x2E, 0x5F, 0xA7, 0xB1, 0xF1, 0xEF, 0x8C, 0xA0, 0xA6, 0x08, 0x0B, 0xF9, 0xDA, 0x37, 0x82, 0xD2, + 0xBD, 0xE4, 0xB3, 0xA3, 0xC6, 0x5C, 0xFB, 0x9F, 0x1B, 0x39, 0x05, 0xB9, 0x36, 0x1D, 0x1E, 0x0C, 0x8F, 0xEB, 0x5A, 0xB4, 0x0A, 0x3F, 0xFE, 0xB3, 0xAE, 0x95, 0xF5, 0x75, 0x62, 0xA0, 0x7C, 0xD2, + 0x43, 0x18, 0xC0, 0xE7, 0xEE, 0x6E, 0xBE, 0x57, 0x0C, 0xB7, 0xDC, 0x1C, 0x62, 0x1A, 0x84, 0x92, 0x13, 0xE7, 0x13, 0x92, 0x42, 0x75, 0x81, 0x28, 0xC1, 0x6C, 0xFE, 0x52, 0xF8, 0xE2, 0xED, 0xA5, + 0xBA, 0x23, 0x23, 0x15, 0x6F, 0x85, 0x3A, 0xBC, 0x61, 0xB1, 0x39, 0x04, 0x1A, 0x4B, 0x83, 0x40, 0x37, 0xAA, 0x19, 0xDC, 0xEE, 0x76, 0x06, 0xAE, 0x84, 0xC1, 0xA7, 0x4D, 0x0E, 0xEB, 0x6A, 0x4D, + 0xAB, 0xD5, 0x90, 0x8D, 0xAE, 0x2C, 0x23, 0xA6, 0x38, 0x76, 0xE7, 0xE9, 0xF8, 0xE9, 0x03, 0x66, 0xA1, 0xFD, 0x89, 0xF2, 0x28, 0x3D, 0x75, 0x30, 0x09, 0xE0, 0x56, 0xDD, 0x5A, 0xB9, 0x53, 0xDB, + 0x3D, 0x8F, 0x48, 0x30, 0xA4, 0xD0, 0x93, 0x79, 0x39, 0x5F, 0x21, 0xED, 0x03, 0xB6, 0xCC, 0xD5, 0xD7, 0xF8, 0xF8, 0x1F, 0x40, 0x0B, 0x3E, 0x3B, 0xC6, 0x96, 0x08, 0x8D, 0x58, 0x17, 0x75, 0x21, + 0x11, 0x0B, 0x6C, 0x84, 0x74, 0xF3, 0xE4, 0x49, 0xD8, 0xEC, 0x7F, 0x46, 0x6C, 0x2E, 0xB3, 0x43, 0x65, 0x9F, 0xF5, 0x33, 0x97, 0x58, 0x7B, 0xC6, 0x30, 0x0D, 0xEE, 0xBD, 0xC2, 0xBE, 0x67, 0x4B, + 0x78, 0x30, 0x90, 0xEA, 0xCC, 0xB9, 0x3B, 0x6A, 0xE9, 0x49, 0x56, 0xA3, 0x33, 0xE8, 0x58, 0x37, 0x64, 0x73, 0xCA, 0x67, 0xAF, 0x05, 0x43, 0xE5, 0x99, 0x94, 0x1E, 0xB4, 0xE8, 0xC6, 0xD9, 0x5D, + 0x47, 0x9F, 0xEE, 0xE0, 0x5E, 0x3E, 0x8B, 0xF5, 0xF0, 0xAA, 0xCD, 0x34, 0x51, 0xC0, 0xED, 0x48, 0x1F, 0x52, 0x6D, 0x38, 0xEB, 0x3B, 0x26, 0xA4, 0xFD, 0x98, 0xE1, 0x1B, 0xAF, 0x67, 0xED, 0xEA, + 0xB2, 0xEC, 0xC7, 0xD3, 0x97, 0xE9, 0x68, 0xF8, 0xD1, 0x03, 0xE8, 0x01, 0x44, 0xA4, 0xCD, 0xB7, 0x00, 0xC4, 0x1A, 0x42, 0x83, 0x4B, 0x07, 0xFD, 0x7E, 0x91, 0xF3, 0xC5, 0x24, 0x09, 0xC6, 0x88, + 0x2C, 0xF4, 0x15, 0xA4, 0x2F, 0x71, 0xE2, 0x1F, 0xE7, 0x00, 0x17, 0xD6, 0x2B, 0x1F, 0xE4, 0x3A, 0x2A, 0x32, 0xD8, 0x15, 0xE3, 0xF1, 0xA4, 0x4E, 0x72, 0x67, 0xB1, 0xBB, 0xF5, 0x52, 0xF3, 0x8E, + 0x88, 0x97, 0x75, 0xEC, 0xD8, 0x5C, 0x4B, 0xF4, 0x65, 0x02, 0x22, 0xF3, 0x30, 0xFA, 0xE4, 0xB6, 0x17, 0x65, 0x52, 0x54, 0x03, 0xFB, 0xDE, 0x0A, 0x18, 0xF9, 0x73, 0x65, 0x7C, 0xAB, 0xEB, 0x05, + 0xFE, 0x6B, 0x97, 0x29, 0xD3, 0xB3, 0x73, 0x0A, 0xEF, 0xDF, 0x3C, 0x18, 0x96, 0x99, 0x7A, 0x94, 0x9B, 0x60, 0x3C, 0x43, 0xFE, 0xCC, 0x3E, 0xAC, 0xCB, 0xF0, 0x0C, 0x03, 0x76, 0x59, 0x41, 0x80, + 0x0C, 0xE4, 0x2F, 0xD0, 0x38, 0x4E, 0x1C, 0x1C, 0x61, 0x17, 0x31, 0x6C, 0xBA, 0x1A, 0x81, 0xA2, 0x09, 0x03, 0x3C, 0x5B, 0x53, 0xAE, 0x3B, 0x60, 0xBC, 0x1A, 0xFC, 0x6E, 0x7C, 0x95, 0xC5, 0xCB, + 0x99, 0xC2, 0x6A, 0x4C, 0x88, 0x1F, 0x62, 0x6A, 0x21, 0x9A, 0x61, 0x9B, 0xC3, 0x5C, 0xF4, 0xEF, 0x0A, 0x3B, 0x67, 0x25, 0x34, 0x9D, 0x2C, 0x13, 0xD8, 0x9D, 0xE6, 0x5D, 0x9F, 0x7A, 0x35, 0x51, + 0xCC, 0xCF, 0xC5, 0x61, 0x1D, 0xC9, 0xC8, 0x73, 0x7B, 0x0E, 0xF0, 0xFA, 0xDF, 0x86, 0x5A, 0x65, 0x33, 0x9F, 0x46, 0x4C, 0xB0, 0x65, 0xBA, 0x8F, 0xE4, 0x81, 0x06, 0x46, 0xA3, 0x44, 0x5B, 0x70, + 0x2F, 0x51, 0xD6, 0xA9, 0x13, 0x49, 0xFD, 0x70, 0xA3, 0x56, 0x49, 0xFD, 0x4D, 0xAE, 0xE6, 0x13, 0x10, 0xA3, 0xCC, 0xA5, 0xED, 0x3A, 0xBD, 0xBF, 0xF8, 0x35, 0x5B, 0x51, 0x14, 0x83, 0x5F, 0xDE, + 0x73, 0xC9, 0xF5, 0x2A, 0xC2, 0x29, 0xB1, 0x5E, 0x84, 0xD3, 0xF5, 0x9D, 0xCB, 0x13, 0x02, 0x55, 0x1E, 0xA4, 0xDD, 0x6F, 0x41, 0x5D, 0x01, 0x39, 0x11, 0xD6, 0x53, 0x15, 0xC8, 0xE5, 0x9B, 0x12, + 0x20, 0x4A, 0xAA, 0xF5, 0x25, 0x75, 0x4E, 0x96, 0xEC, 0x3C, 0xB1, 0x3E, 0x19, 0x72, 0x62, 0x1F, 0x9C, 0x86, 0xF5, 0xDE, 0x4A, 0xDA, 0xB9, 0x80, 0xCF, 0x83, 0x69, 0x12, 0x7C, 0x2B, 0x3E, 0x4E, + 0xF1, 0xA8, 0x2B, 0x7A, 0xC9, 0x59, 0xAB, 0x45, 0xD9, 0x7E, 0xEE, 0x7A, 0x14, 0xE4, 0x14, 0x5B, 0x34, 0x9B, 0x53, 0x3D, 0xD9, 0x2D, 0xD2, 0xC1, 0x77, 0xC7, 0x7A, 0xBA, 0x32, 0x5D, 0xD7, 0x5C, + 0x77, 0xB3, 0x1A, 0x6A, 0xB3, 0xAA, 0xBE, 0x54, 0xA6, 0xCF, 0xA2, 0xDC, 0xA3, 0x5E, 0x20, 0x99, 0x35, 0xEF, 0x9D, 0x94, 0x7A, 0x37, 0xE8, 0x35, 0x97, 0xB9, 0x4F, 0xCA, 0xF5, 0x8A, 0x56, 0xD1, + 0x4A, 0x05, 0x69, 0x12, 0xC2, 0x2A, 0x54, 0xA6, 0xFF, 0x2F, 0xE8, 0x25, 0xBA, 0xAD, 0x8A, 0xBF, 0x1D, 0xD8, 0x7F, 0xB0, 0xFA, 0x15, 0x19, 0xA5, 0xB7, 0xB4, 0x2F, 0x4B, 0xB2, 0xF7, 0x57, 0xEF, + 0xF7, 0xC1, 0x2A, 0x2C, 0xD1, 0xB9, 0x1F, 0xAE, 0xBF, 0x80, 0x86, 0x51, 0x6D, 0xCD, 0xD5, 0x5F, 0x63, 0x84, 0x18, 0x8F, 0x53, 0xC6, 0xA7, 0x81, 0x86, 0x2F, 0xB5, 0xCC, 0x3C, 0xC6, 0x1A, 0xDE, + 0x2F, 0x11, 0x08, 0xD1, 0x51, 0x63, 0xC3, 0x8C, 0x4C, 0xA0, 0x1B, 0xF7, 0xF2, 0xC8, 0x1B, 0x8C, 0x79, 0xAD, 0x69, 0x4A, 0x01, 0x61, 0x7B, 0xC0, 0x4F, 0x84, 0x70, 0xC2, 0xC7, 0x71, 0xBE, 0xE2, + 0x9A, 0x66, 0x6B, 0xE8, 0x51, 0x42, 0xCB, 0x96, 0x7E, 0xC5, 0x69, 0xA4, 0x02, 0x2A, 0x64, 0xFC, 0x5D, 0x95, 0xA5, 0x57, 0x76, 0xAC, 0x73, 0x27, 0x55, 0xB2, 0x39, 0x29, 0xF2, 0x59, 0x86, 0xD9, + 0x3C, 0x01, 0x9B, 0xBB, 0xFB, 0x15, 0x4C, 0x26, 0xBB, 0x47, 0xA2, 0xBA, 0x4B, 0x32, 0x97, 0xDC, 0xE4, 0x47, 0xC5, 0x61, 0xA1, 0xC4, 0x9F, 0x75, 0x35, 0xA7, 0xA1, 0x4C, 0x98, 0x30, 0x18, 0x6A, + 0xA0, 0xDD, 0xFA, 0x00, 0x1A, 0xEA, 0x0D, 0x94, 0xC4, 0x0A, 0xC8, 0xA8, 0x41, 0x8E, 0x8D, 0x57, 0x8D, 0x84, 0x21, 0x41, 0x3F, 0xB7, 0xE8, 0x20, 0x23, 0x7E, 0xF3, 0xB5, 0xCB, 0xF6, 0x08, 0x1C, + 0x44, 0x2C, 0x13, 0xB4, 0x98, 0x5E, 0xE6, 0x39, 0xE8, 0xF8, 0x6D, 0xB2, 0x87, 0x3B, 0xC2, 0xC9, 0xD3, 0xA9, 0xE5, 0x17, 0xAD, 0x70, 0x31, 0xDA, 0x3C, 0xC9, 0x2F, 0xC1, 0x5F, 0x50, 0x2F, 0xAD, + 0x3F, 0xC5, 0xFD, 0xBB, 0xCD, 0x2C, 0x95, 0x50, 0xA8, 0x95, 0x25, 0xF0, 0x06, 0x7C, 0xC3, 0xEA, 0x22, 0xD8, 0xD5, 0xB6, 0x1A, 0xFA, 0xA4, 0xB5, 0x53, 0xAC, 0x30, 0x39, 0x20, 0xF2, 0x5D, 0x6D, + 0x58, 0xF6, 0x1F, 0x63, 0x56, 0x68, 0x5E, 0x43, 0x50, 0x9A, 0x00, 0x62, 0xF8, 0x37, 0xBC, 0xB9, 0xA1, 0xA2, 0x2C, 0xFF, 0x08, 0x10, 0x80, 0x18, 0xD6, 0xD2, 0x4B, 0xDC, 0x2B, 0x09, 0x6D, 0x2E, + }, + .t1_len = 2560, + .t1 = { + 0x03, 0x23, 0x69, 0xA2, 0xCE, 0x57, 0x2F, 0xD0, 0x8B, 0xFC, 0x30, 0x4B, 0x48, 0x48, 0xE7, 0x8D, 0x75, 0x2D, 0x77, 0xE9, 0x7A, 0x28, 0xB9, 0x9B, 0x9B, 0xB6, 0xFB, 0x5C, 0x7C, 0x63, 0x37, 0x51, + 0x4B, 0x32, 0x1E, 0xCD, 0xC1, 0xFB, 0x66, 0x9F, 0x26, 0xD4, 0x17, 0x1A, 0xB4, 0x2B, 0x72, 0x72, 0x0E, 0xE7, 0x0E, 0x05, 0x19, 0xA6, 0xE1, 0xD3, 0xD6, 0xD9, 0x91, 0x4E, 0xC1, 0xB2, 0x1C, 0xDE, + 0x38, 0xB4, 0x1A, 0xAC, 0x1D, 0x3A, 0xBE, 0xE6, 0xF2, 0xB7, 0x49, 0x5C, 0x4C, 0x82, 0x0C, 0x1F, 0xC0, 0xCC, 0x9E, 0x71, 0xE2, 0x4C, 0xFB, 0x5C, 0x9C, 0x0D, 0x8E, 0xEF, 0x42, 0x64, 0xAF, 0x48, + 0x4F, 0xAE, 0x4D, 0x6E, 0x5D, 0xDE, 0x65, 0xD4, 0xDF, 0x72, 0xB6, 0x1C, 0x6D, 0xBD, 0x26, 0xF8, 0x61, 0xA5, 0xE0, 0xB8, 0x53, 0xAC, 0x54, 0x13, 0x22, 0x6F, 0xEB, 0xBA, 0xBA, 0x5E, 0xB4, 0x74, + 0xC6, 0xFB, 0x25, 0xA8, 0x26, 0x78, 0xEA, 0x16, 0x06, 0xB4, 0x52, 0xA2, 0x31, 0x12, 0x22, 0x10, 0x17, 0xB8, 0xC0, 0x73, 0xC1, 0x03, 0x78, 0xF9, 0x14, 0x56, 0x41, 0xA8, 0xC0, 0x78, 0xC0, 0xED, + 0x9E, 0x42, 0x16, 0x50, 0xF7, 0x48, 0x89, 0x25, 0x22, 0xAB, 0x9F, 0xB7, 0xD1, 0xFF, 0x8C, 0xF1, 0xCC, 0x71, 0xB8, 0x56, 0x6E, 0x8D, 0xA3, 0x3C, 0xD7, 0x36, 0x17, 0x70, 0xC0, 0x44, 0x34, 0x9A, + 0xC4, 0x40, 0xCC, 0xCD, 0xC6, 0xBB, 0xE3, 0x5E, 0x6C, 0x55, 0x78, 0x27, 0x66, 0xF3, 0x8E, 0x68, 0x8B, 0xF4, 0x78, 0x21, 0x03, 0x72, 0x99, 0xE3, 0x44, 0xEC, 0xDE, 0xCA, 0x17, 0xAD, 0x5D, 0x15, + 0xCD, 0x27, 0xA4, 0xF7, 0xB0, 0x70, 0x66, 0x11, 0x38, 0xED, 0xE8, 0xED, 0x72, 0xA8, 0x95, 0x9C, 0x5A, 0xE3, 0x6B, 0x1C, 0x46, 0x09, 0x4A, 0x53, 0xCB, 0x21, 0xA7, 0xA4, 0x26, 0x73, 0xF1, 0x40, + 0x1C, 0x2B, 0x25, 0x94, 0x94, 0x09, 0x0E, 0x2F, 0x53, 0xD7, 0xEE, 0x70, 0x63, 0x43, 0x1E, 0xE5, 0x85, 0x80, 0x02, 0xD8, 0x50, 0xAF, 0x90, 0x9C, 0x37, 0x83, 0x43, 0x60, 0x10, 0xF7, 0xEA, 0x88, + 0x62, 0x5A, 0x36, 0xA0, 0xF0, 0x18, 0x9F, 0xDE, 0x75, 0xB7, 0xE8, 0xC7, 0xE4, 0xB1, 0x9D, 0x85, 0x27, 0x00, 0x83, 0x28, 0xAD, 0xBC, 0x92, 0x9B, 0xBC, 0x86, 0xE9, 0x64, 0xCF, 0xC4, 0x8B, 0x8C, + 0xF1, 0xDA, 0x5D, 0x7E, 0xD3, 0x33, 0x3A, 0xB5, 0x5C, 0x15, 0x07, 0x28, 0x32, 0x21, 0x4A, 0x77, 0x9A, 0x5F, 0xD1, 0x0C, 0xC0, 0x40, 0x05, 0xF4, 0x6C, 0x1A, 0xA8, 0x88, 0x4A, 0x16, 0x19, 0x92, + 0x47, 0x2F, 0xD5, 0x35, 0xB9, 0x5E, 0xD1, 0x8B, 0xDE, 0x1C, 0x6D, 0x8C, 0xE6, 0x78, 0xD2, 0x81, 0x7D, 0x69, 0xF9, 0x05, 0x71, 0x10, 0x3E, 0x85, 0x20, 0xE7, 0x31, 0x3C, 0xE7, 0xB9, 0x30, 0xC5, + 0xEB, 0xFA, 0xF2, 0xF4, 0xEC, 0x75, 0x8B, 0x62, 0x6B, 0x55, 0x43, 0xA0, 0x68, 0xCD, 0xE0, 0xFD, 0x0E, 0x94, 0xE6, 0xA6, 0x44, 0x75, 0xB2, 0x32, 0x68, 0xBF, 0x03, 0x80, 0xD0, 0x75, 0x50, 0x8F, + 0x85, 0x12, 0x8C, 0xA2, 0x6F, 0x31, 0xA9, 0x0C, 0x4A, 0x7D, 0x28, 0x44, 0x0D, 0x54, 0xD4, 0x06, 0x6B, 0x40, 0x45, 0x88, 0x58, 0x8B, 0x4C, 0xCF, 0x85, 0x0B, 0x97, 0x5C, 0x73, 0xAF, 0xE6, 0x8C, + 0xBC, 0xD1, 0x02, 0x75, 0x5F, 0x61, 0xEB, 0x3E, 0x60, 0x32, 0x3C, 0x57, 0x6E, 0x52, 0x9E, 0xC0, 0xBF, 0x23, 0xBF, 0xA5, 0xBE, 0xA3, 0x9C, 0xB7, 0x3C, 0x37, 0xE8, 0x39, 0x5D, 0x8D, 0xBD, 0x4C, + 0x8D, 0xC8, 0xAB, 0x2F, 0x70, 0xA0, 0xBF, 0xC3, 0xA7, 0x8C, 0x0D, 0x41, 0x3F, 0x08, 0xD1, 0x4D, 0x63, 0x2B, 0xC0, 0x40, 0x3B, 0x03, 0x83, 0xDB, 0xBB, 0x22, 0xBD, 0x9B, 0x11, 0x3C, 0x89, 0x45, + 0x2A, 0xEA, 0xB1, 0x12, 0x10, 0x09, 0x79, 0x47, 0xFE, 0xAA, 0xA3, 0xC9, 0xF0, 0x5D, 0x1D, 0x30, 0x0C, 0x33, 0xA5, 0x5E, 0x3F, 0xBC, 0x81, 0x25, 0x9E, 0x86, 0x27, 0x05, 0xC3, 0xA1, 0x3B, 0x9E, + 0xE3, 0x5F, 0x6B, 0x23, 0xED, 0x10, 0xF4, 0xED, 0xEA, 0x95, 0x19, 0xFA, 0x91, 0xB7, 0xBC, 0xD0, 0xD5, 0x01, 0xB5, 0xED, 0x57, 0xD9, 0x04, 0x9F, 0xAB, 0x91, 0xAA, 0x77, 0x9C, 0x72, 0x5F, 0xF8, + 0xE9, 0xF7, 0x80, 0x17, 0xEA, 0x78, 0x07, 0xFA, 0x25, 0x4B, 0x71, 0x05, 0xE8, 0x26, 0xD0, 0x96, 0xC0, 0x1A, 0xDA, 0xE2, 0xC5, 0xD1, 0x38, 0x25, 0x1A, 0x92, 0xA4, 0x78, 0xA3, 0x33, 0x73, 0xF4, + 0xDE, 0x91, 0x2B, 0x83, 0xB6, 0xFB, 0x4B, 0x0D, 0x0D, 0xE6, 0xBC, 0x11, 0x18, 0xBB, 0x2F, 0xCF, 0xB0, 0x7B, 0xD2, 0x27, 0xA5, 0xF7, 0xF9, 0x91, 0x43, 0x9A, 0x13, 0xDE, 0x12, 0x38, 0x18, 0x0C, + 0xDC, 0x55, 0x11, 0x9E, 0x65, 0xC4, 0x18, 0x58, 0x4D, 0x80, 0x7A, 0x92, 0x6E, 0x4A, 0x9C, 0x0F, 0x70, 0x15, 0x5E, 0xE1, 0x96, 0xFB, 0x07, 0x65, 0x6D, 0x9A, 0xA7, 0x98, 0x2B, 0x87, 0x95, 0xDB, + 0xAD, 0x43, 0xD1, 0x05, 0x9C, 0xA7, 0xF5, 0x80, 0xD3, 0x32, 0x0C, 0x04, 0x38, 0xA5, 0xED, 0x5A, 0x70, 0x32, 0xB2, 0xE9, 0x59, 0x67, 0x84, 0x10, 0xF1, 0x1A, 0xD9, 0x8B, 0xE8, 0x82, 0x6A, 0x44, + 0x26, 0x26, 0x15, 0x64, 0x5D, 0x75, 0x9A, 0x86, 0x2B, 0x2A, 0xC5, 0x2D, 0x3B, 0x01, 0x4A, 0x25, 0xE8, 0x47, 0x3F, 0x1F, 0x1E, 0xA4, 0xCF, 0xA8, 0x19, 0x93, 0x0A, 0xB3, 0xA3, 0x4D, 0x71, 0x0D, + 0xEE, 0xE7, 0x0C, 0xA1, 0x3E, 0x88, 0xFD, 0x71, 0xAA, 0x06, 0x4E, 0x6C, 0xB4, 0x69, 0x7D, 0xE0, 0xE4, 0x63, 0xB1, 0x37, 0x0A, 0x6A, 0x3B, 0xFE, 0x98, 0xFD, 0xFE, 0x7B, 0x54, 0x71, 0xFF, 0x8D, + 0xF6, 0xA6, 0x87, 0x9F, 0xBE, 0xF9, 0xAF, 0xB3, 0x51, 0x9D, 0x78, 0x07, 0x57, 0xD6, 0x74, 0x40, 0xAC, 0x36, 0xE8, 0x37, 0xBA, 0xC3, 0x83, 0x3E, 0xEA, 0xA9, 0x80, 0xBD, 0x82, 0xB7, 0x93, 0x64, + 0x36, 0xA0, 0x30, 0x7D, 0x16, 0x4B, 0x64, 0x38, 0x86, 0x9A, 0xE6, 0x06, 0xE9, 0x80, 0x51, 0x8E, 0x91, 0x3D, 0x0E, 0xE3, 0x02, 0x39, 0x6E, 0xF4, 0xEB, 0x25, 0xD9, 0x86, 0x6E, 0x4B, 0xAF, 0xA1, + 0x01, 0xE5, 0x99, 0x29, 0x31, 0x36, 0x1C, 0x4A, 0x98, 0x22, 0x53, 0xD5, 0x8A, 0xBE, 0x3B, 0xD5, 0x71, 0x07, 0x63, 0x5A, 0x46, 0xF0, 0x95, 0x12, 0x08, 0x5F, 0x4A, 0xDA, 0x08, 0xEC, 0x8B, 0x1B, + 0x39, 0x10, 0xB0, 0x15, 0x3B, 0x2A, 0xAF, 0xCA, 0xE5, 0x03, 0x3E, 0xDD, 0x41, 0x53, 0x24, 0x8D, 0xCD, 0x85, 0xB0, 0x2C, 0x9A, 0x25, 0xD8, 0xBD, 0xC4, 0x06, 0x8B, 0xB8, 0x57, 0x41, 0x72, 0x62, + 0x97, 0xA2, 0x5A, 0xEC, 0x55, 0xC4, 0x4A, 0xA2, 0x80, 0x59, 0xB7, 0x1B, 0xB9, 0xF3, 0x40, 0x67, 0x88, 0x7A, 0xDE, 0x4C, 0x1C, 0xA4, 0x90, 0x8B, 0x19, 0xB3, 0xD7, 0x81, 0x23, 0x45, 0x38, 0x76, + 0xDB, 0x4D, 0xCE, 0xB4, 0x27, 0x73, 0x06, 0x95, 0x72, 0xCD, 0x87, 0x77, 0xE6, 0x2C, 0xFB, 0xAF, 0x72, 0x03, 0xF0, 0x20, 0xF2, 0x81, 0xA6, 0x67, 0x8F, 0x79, 0x07, 0x20, 0xEA, 0xA2, 0x0E, 0x34, + 0x32, 0x7D, 0x7A, 0x63, 0x68, 0x8B, 0x09, 0xA0, 0x1F, 0x4D, 0x70, 0x88, 0xF7, 0xB5, 0x05, 0x9E, 0xDD, 0xEB, 0x45, 0xC0, 0xCE, 0x39, 0x32, 0x1C, 0x79, 0x52, 0x1D, 0x79, 0xA5, 0x9E, 0xCD, 0xD4, + 0x68, 0xCE, 0xD0, 0xEA, 0x82, 0xCA, 0x48, 0x49, 0x28, 0x70, 0x2F, 0x57, 0xD6, 0xFC, 0x18, 0xD3, 0x47, 0xAF, 0x3E, 0xD2, 0x2A, 0xAF, 0x45, 0xAB, 0xB0, 0xF2, 0x0B, 0xAB, 0x9E, 0x01, 0x55, 0x76, + 0x07, 0xAE, 0x3E, 0xD9, 0xCF, 0x0E, 0x26, 0xD3, 0x4D, 0x30, 0x54, 0x49, 0x66, 0x9E, 0xC6, 0xFC, 0x1B, 0xEC, 0xEA, 0xDC, 0xE1, 0x83, 0xF7, 0xA5, 0x94, 0xCE, 0xA1, 0x96, 0xD0, 0x59, 0xA1, 0xE5, + 0x50, 0xE5, 0x47, 0x86, 0x6C, 0xC0, 0x87, 0x33, 0x3F, 0x03, 0x0E, 0x62, 0x8F, 0x2C, 0xF1, 0x14, 0x79, 0x25, 0x41, 0x0E, 0xD0, 0x42, 0x1D, 0xC7, 0x50, 0x61, 0x38, 0xB1, 0xD1, 0x90, 0x99, 0xC6, + 0x95, 0xE1, 0xAF, 0xDA, 0xCE, 0x41, 0x53, 0x82, 0x5B, 0x66, 0xA8, 0xEC, 0xF5, 0x5A, 0x02, 0x1D, 0x21, 0xEB, 0x9F, 0x84, 0x8F, 0xE5, 0x5C, 0x21, 0x76, 0x9A, 0x75, 0x5F, 0xA9, 0x80, 0x7E, 0xF7, + 0x3A, 0x6C, 0x5B, 0xA1, 0x5A, 0x06, 0x34, 0x7D, 0x3F, 0x1C, 0x5C, 0x61, 0x9A, 0x31, 0x55, 0x98, 0x62, 0x91, 0x06, 0xAC, 0x0B, 0x86, 0xAE, 0x0D, 0x8E, 0x55, 0x57, 0x82, 0x92, 0x51, 0x72, 0x58, + 0xAE, 0x85, 0xF7, 0x2E, 0x73, 0x7A, 0xF5, 0x63, 0x8D, 0x09, 0x6B, 0x76, 0xA3, 0xC5, 0x7F, 0x1B, 0x9C, 0x80, 0xE7, 0x70, 0xA2, 0xD4, 0xEA, 0x4E, 0x42, 0xFE, 0x46, 0x9A, 0xD4, 0x21, 0x28, 0x52, + 0x41, 0x96, 0x0A, 0x8A, 0x86, 0x35, 0x5E, 0xF2, 0x2F, 0x58, 0x3F, 0xE3, 0xBA, 0xCA, 0xDF, 0x8D, 0xA3, 0x1D, 0x5C, 0x2D, 0xE2, 0x54, 0x16, 0x1B, 0xC6, 0xD1, 0x0F, 0x98, 0x41, 0xDD, 0x27, 0xED, + 0x46, 0x2A, 0x6B, 0x94, 0xB6, 0xDE, 0xEA, 0x90, 0xCB, 0xAB, 0x68, 0x7F, 0xB8, 0x4B, 0x56, 0x39, 0x5D, 0xA7, 0x63, 0xAB, 0x4B, 0x7F, 0xE3, 0x09, 0x5D, 0x57, 0x2D, 0x77, 0xEF, 0xF3, 0xFF, 0x0D, + 0x8F, 0x9D, 0x19, 0xAA, 0x5A, 0xF7, 0xB6, 0x76, 0x05, 0x3D, 0xBE, 0xF6, 0x4E, 0x61, 0xDD, 0x0A, 0x41, 0xD4, 0x02, 0x31, 0x8E, 0x33, 0x08, 0x66, 0x91, 0x06, 0x25, 0x9B, 0xF7, 0xA4, 0xCE, 0x31, + 0xB3, 0x46, 0xA9, 0xE9, 0x83, 0xED, 0xAB, 0xA0, 0x51, 0x80, 0x14, 0x9A, 0xB0, 0x57, 0xF9, 0x97, 0x29, 0x77, 0xDA, 0x7C, 0x6F, 0x46, 0xE0, 0xCD, 0xF8, 0x6F, 0x30, 0x91, 0xF0, 0x4F, 0xD4, 0xE8, + 0x3C, 0x60, 0x22, 0xE1, 0x8C, 0xE4, 0x38, 0x2B, 0x54, 0xD5, 0xDA, 0xBA, 0x82, 0xE4, 0xDF, 0x1E, 0x53, 0xBF, 0x31, 0xFE, 0x4B, 0xB6, 0x5A, 0x85, 0x24, 0xED, 0xA8, 0x3F, 0xD2, 0x9D, 0x07, 0xE4, + 0x97, 0x47, 0xB7, 0x52, 0x91, 0xCB, 0xC8, 0xF8, 0xEE, 0x14, 0x15, 0xEC, 0x92, 0x1E, 0x19, 0x02, 0x2A, 0xDE, 0x2C, 0x04, 0x7E, 0x4D, 0xF3, 0x50, 0x72, 0x89, 0xE9, 0xD7, 0x9A, 0x8E, 0x69, 0x92, + 0xB4, 0x8B, 0x88, 0x64, 0x20, 0x4A, 0x41, 0x6B, 0x76, 0x9C, 0xC7, 0x87, 0xD6, 0xDF, 0x44, 0x07, 0xE9, 0x3D, 0x12, 0x1F, 0x7F, 0xBE, 0xE0, 0xE4, 0x08, 0x96, 0x3E, 0x06, 0x09, 0xA9, 0xC7, 0x5C, + 0xB3, 0x11, 0x7C, 0xA5, 0x83, 0xDF, 0x6E, 0x79, 0xF3, 0x1C, 0x63, 0x5B, 0xF0, 0xF1, 0xBE, 0x98, 0xDF, 0x55, 0x07, 0x27, 0xA4, 0x5D, 0x3C, 0xA3, 0x37, 0xD7, 0x9D, 0xE5, 0xDC, 0xDB, 0x0B, 0x91, + 0xCA, 0xBB, 0xC3, 0x0D, 0x7E, 0xF0, 0xAE, 0x1C, 0xA1, 0xE9, 0x49, 0x04, 0xF7, 0x8C, 0x1F, 0xD8, 0xFB, 0xA8, 0x75, 0x45, 0xFD, 0xC1, 0x74, 0xAD, 0x81, 0x90, 0xF9, 0xB5, 0xED, 0x7B, 0x58, 0x69, + 0x49, 0x4F, 0xFA, 0x91, 0x03, 0x3F, 0xDC, 0x61, 0x17, 0xBF, 0x66, 0x2E, 0xC5, 0xF2, 0xAF, 0x26, 0x34, 0xBA, 0x3F, 0x8C, 0x02, 0x21, 0x0F, 0x1C, 0x9B, 0xCD, 0xDA, 0x9B, 0xB3, 0x97, 0x60, 0xE0, + 0x0F, 0x25, 0xA7, 0x27, 0x0C, 0x34, 0x56, 0x66, 0xFB, 0x6D, 0xF8, 0x5C, 0x91, 0x9A, 0xA1, 0x50, 0xCA, 0x7F, 0xC8, 0x0F, 0xC0, 0xEA, 0xCF, 0xE2, 0x42, 0xEF, 0x55, 0xF4, 0x29, 0x80, 0x63, 0x62, + 0x8E, 0x61, 0x05, 0x6C, 0x96, 0x6D, 0xB9, 0x96, 0x44, 0x28, 0xD9, 0xCE, 0x99, 0x10, 0x82, 0x71, 0xE2, 0x9A, 0x12, 0x32, 0x8E, 0x23, 0x99, 0x97, 0x34, 0xE0, 0x36, 0xF1, 0x8A, 0x0E, 0xB8, 0xF0, + 0x30, 0xE8, 0x80, 0x62, 0xC5, 0x67, 0x17, 0xE7, 0xA3, 0x63, 0x14, 0xE4, 0x4E, 0xCF, 0x35, 0x7F, 0xF5, 0x6E, 0xED, 0xF9, 0x0D, 0x3F, 0xB1, 0x1B, 0x22, 0xA1, 0xB2, 0x59, 0x05, 0xB3, 0x79, 0xFC, + 0xCA, 0x5C, 0xA1, 0xAC, 0xB9, 0x56, 0xE1, 0x78, 0xAD, 0x3F, 0x51, 0xD5, 0x35, 0xAD, 0x11, 0x98, 0x13, 0xB1, 0xE7, 0x0F, 0x73, 0x17, 0x65, 0x1B, 0xC7, 0x5C, 0xAC, 0x64, 0x27, 0x6B, 0xB9, 0x81, + 0x10, 0xB5, 0x4E, 0xA0, 0xEF, 0x34, 0x54, 0x1D, 0x73, 0x91, 0x07, 0x21, 0xD6, 0x57, 0x38, 0x76, 0x77, 0xE3, 0x32, 0xE9, 0xC8, 0x81, 0x1C, 0x3F, 0xC1, 0xB9, 0x23, 0xB2, 0xEE, 0x9C, 0x51, 0x2F, + 0x6D, 0x09, 0xDF, 0x37, 0x2A, 0x5F, 0x97, 0xFA, 0xD7, 0x12, 0x33, 0x89, 0xCE, 0xE1, 0x97, 0xB5, 0xC2, 0x69, 0xE2, 0x21, 0xD7, 0xEE, 0xD3, 0x16, 0x0A, 0x52, 0x1E, 0x56, 0xFF, 0x8A, 0xAF, 0xAB, + 0x68, 0x61, 0x79, 0xD0, 0x9D, 0x78, 0xFC, 0x38, 0x7B, 0x3E, 0xA6, 0xA6, 0x72, 0x03, 0x4D, 0x24, 0xAC, 0x79, 0x99, 0xD1, 0x96, 0xB2, 0x31, 0x64, 0x75, 0xF3, 0x7D, 0xB8, 0xE9, 0xED, 0x43, 0x1D, + 0xF5, 0x83, 0x41, 0xFA, 0x88, 0x00, 0x3D, 0x3C, 0x64, 0x89, 0xE7, 0x80, 0x53, 0xD8, 0xE4, 0x4C, 0xE7, 0xE1, 0x6A, 0xEF, 0x41, 0x68, 0x59, 0xB3, 0xD2, 0xAE, 0xCE, 0x09, 0x08, 0x6A, 0x74, 0x8B, + 0x7B, 0xCF, 0xD1, 0x0F, 0x73, 0xE3, 0xCF, 0x8B, 0x31, 0xF0, 0xCC, 0x44, 0xDA, 0x05, 0x9C, 0x69, 0xAB, 0xA5, 0xBC, 0x8E, 0xFA, 0xD4, 0x5D, 0x3F, 0x37, 0x6A, 0xF3, 0xA0, 0xDE, 0x6E, 0x16, 0x98, + 0x78, 0xBD, 0x84, 0x2E, 0x28, 0x79, 0x8E, 0x47, 0x43, 0xF8, 0x43, 0x84, 0x4B, 0xCD, 0xF8, 0x50, 0x6F, 0x13, 0x63, 0x91, 0xEC, 0x8E, 0x72, 0x1D, 0xC2, 0xB6, 0x28, 0x2D, 0x9C, 0x50, 0xFA, 0xB6, + 0x53, 0xA6, 0xAB, 0xF2, 0x89, 0x47, 0x42, 0x0E, 0x8C, 0x22, 0xA9, 0xA4, 0x87, 0xD7, 0x6A, 0x93, 0x89, 0x33, 0xB3, 0x4E, 0x49, 0x7D, 0xA9, 0x53, 0x94, 0x17, 0x6B, 0x27, 0x74, 0xC0, 0x9E, 0xF0, + 0xBB, 0x1E, 0xD8, 0xC3, 0xB1, 0x31, 0xA2, 0x19, 0x57, 0xB3, 0x1A, 0x0B, 0x47, 0xCB, 0xFB, 0xFF, 0x05, 0x33, 0xCA, 0xF3, 0x31, 0x25, 0x22, 0x1D, 0xB6, 0xBA, 0x4A, 0x51, 0x88, 0x64, 0x89, 0x2C, + 0xF2, 0x1D, 0x3D, 0x4D, 0x58, 0xB5, 0x99, 0xA3, 0x7A, 0x08, 0xF3, 0x44, 0xAA, 0x7E, 0xF9, 0x8E, 0x7D, 0x7D, 0x9D, 0x33, 0x16, 0xA6, 0xB1, 0x15, 0xD9, 0xB8, 0xF2, 0x0F, 0x93, 0xBC, 0x68, 0x65, + 0x73, 0x46, 0x99, 0xEB, 0x54, 0xC8, 0x88, 0xD7, 0xE5, 0xA0, 0xAC, 0xAF, 0xD1, 0x91, 0x53, 0x52, 0xB2, 0x94, 0x24, 0x37, 0x12, 0xCF, 0xE8, 0x2F, 0x85, 0x24, 0x8B, 0x00, 0x04, 0x5C, 0xF3, 0xD0, + 0x90, 0xC0, 0xC0, 0x0D, 0x7C, 0xA0, 0xE3, 0xA1, 0xF1, 0x47, 0x70, 0x3F, 0xD9, 0x4F, 0x71, 0x7E, 0x49, 0xC8, 0x1A, 0x7C, 0x3A, 0x76, 0x94, 0x6E, 0x20, 0xA6, 0x3F, 0x3B, 0x7C, 0x3E, 0xAB, 0xA9, + 0x22, 0x5A, 0xBE, 0x0B, 0x34, 0xCB, 0x0C, 0xF2, 0x35, 0x06, 0x39, 0x67, 0xD1, 0x6B, 0xC8, 0xA6, 0x9C, 0x13, 0x0C, 0xCE, 0x28, 0x76, 0x15, 0xCC, 0x05, 0x31, 0x14, 0x16, 0x7E, 0xAC, 0x4E, 0x95, + 0xBB, 0xAB, 0xDF, 0xBB, 0xCF, 0x96, 0xBC, 0x0C, 0x0D, 0x65, 0xEA, 0x00, 0x0A, 0xEA, 0xF4, 0x90, 0xD7, 0x23, 0x95, 0x5B, 0xD1, 0xB4, 0xD6, 0x91, 0x54, 0xD2, 0x62, 0xF6, 0xA6, 0xD3, 0x53, 0x4B, + 0xB0, 0xBC, 0x39, 0x7C, 0x29, 0xEC, 0xC6, 0xB1, 0x44, 0x7B, 0x75, 0xC9, 0x53, 0xAF, 0x44, 0x1D, 0xE2, 0xE7, 0x13, 0x3A, 0x7A, 0xC9, 0x89, 0x88, 0xA7, 0xEF, 0x9E, 0x6E, 0xE6, 0x35, 0x58, 0xAA, + 0xAD, 0xA0, 0x60, 0x3B, 0xD5, 0x29, 0x77, 0x6F, 0x05, 0x55, 0x8D, 0x2D, 0xF5, 0x64, 0x1C, 0x41, 0x2E, 0x73, 0x47, 0x44, 0x0F, 0x65, 0xEB, 0x82, 0x3A, 0xFC, 0x7C, 0xCA, 0xE6, 0xB9, 0x71, 0x08, + 0xB8, 0x57, 0x28, 0x7A, 0x04, 0x86, 0xDB, 0xBE, 0x68, 0x9D, 0x77, 0x0C, 0xA9, 0x24, 0x71, 0x30, 0x9E, 0x73, 0xAD, 0x39, 0x0A, 0xBF, 0x56, 0x91, 0x2B, 0x2B, 0x7C, 0x49, 0x24, 0x2C, 0xEC, 0x15, + 0x7B, 0xDB, 0xBD, 0x49, 0x35, 0x53, 0x73, 0x5C, 0xB1, 0xD9, 0xB4, 0x0A, 0xFC, 0x21, 0x4D, 0xA1, 0x53, 0x35, 0x9C, 0x9D, 0xF5, 0x76, 0x13, 0x59, 0x01, 0xC2, 0xFD, 0xA5, 0x8C, 0x00, 0x95, 0xB6, + 0xFC, 0xE3, 0xFD, 0x07, 0x31, 0xDF, 0x34, 0x86, 0x3A, 0xF2, 0x88, 0x2D, 0x53, 0x77, 0x3C, 0xE7, 0xC1, 0x82, 0x47, 0x37, 0x22, 0xAA, 0x79, 0xA6, 0xB3, 0x7D, 0x3E, 0xDD, 0xDE, 0x38, 0xFA, 0x71, + 0xDF, 0x8C, 0x0E, 0xDC, 0x08, 0x1E, 0xFE, 0xD8, 0xCE, 0x60, 0x6E, 0x48, 0x29, 0x91, 0x80, 0xEC, 0x6F, 0xE3, 0x5F, 0xAB, 0x64, 0x99, 0x10, 0xC4, 0x8A, 0x6A, 0x29, 0xF9, 0xD0, 0xF8, 0x55, 0x57, + 0xE1, 0x0B, 0xC5, 0xAE, 0x2E, 0xCF, 0x02, 0x8A, 0xE3, 0x99, 0xF5, 0x5C, 0xD7, 0x97, 0x60, 0x28, 0x93, 0x5C, 0xC0, 0x3C, 0x0C, 0xAF, 0xD5, 0x00, 0x3C, 0x9E, 0xAE, 0xD2, 0x47, 0xFB, 0xE3, 0x0A, + 0x28, 0x4C, 0xC4, 0x47, 0x0A, 0x55, 0x25, 0xA6, 0x49, 0x8E, 0x1D, 0xBB, 0xD3, 0x08, 0x5C, 0x3F, 0x9D, 0x77, 0xC6, 0x06, 0x4D, 0x01, 0x81, 0xBC, 0x5A, 0x82, 0x95, 0x61, 0x56, 0x0A, 0xA9, 0xA4, + 0xEA, 0x81, 0x73, 0xD7, 0x93, 0x7A, 0x94, 0x28, 0x10, 0x9C, 0xB3, 0xA6, 0x6B, 0x2B, 0x3D, 0xE1, 0x1F, 0x88, 0xF5, 0x5A, 0xB2, 0x1E, 0xB4, 0x9B, 0x77, 0xA3, 0x97, 0x62, 0xCA, 0x92, 0x64, 0xE0, + 0x15, 0x65, 0x66, 0x76, 0x5E, 0x2D, 0x36, 0x26, 0xB7, 0x2B, 0x80, 0xBD, 0x14, 0x11, 0xE4, 0xEC, 0x53, 0x55, 0x28, 0x28, 0xA2, 0x4B, 0xC8, 0xCD, 0xC4, 0x7F, 0x46, 0x5F, 0xDD, 0xF4, 0x77, 0x2C, + 0x7B, 0xC0, 0x20, 0x66, 0x85, 0x40, 0x11, 0x28, 0x7F, 0x73, 0x9A, 0xBA, 0x60, 0x47, 0x59, 0x67, 0x47, 0xF4, 0x23, 0x4A, 0xE2, 0x27, 0xDB, 0xFF, 0xAB, 0xF0, 0xE1, 0x31, 0x53, 0xE2, 0xE0, 0x69, + 0xF0, 0xB7, 0x90, 0x25, 0x1B, 0xE8, 0x77, 0xFE, 0x5A, 0x19, 0x8E, 0x80, 0x82, 0x58, 0x63, 0x9F, 0x5E, 0x79, 0xD3, 0xD5, 0xCD, 0x16, 0xF1, 0xA5, 0x73, 0x72, 0x4D, 0xD6, 0xA9, 0xF6, 0x99, 0x0C, + 0x45, 0x02, 0x33, 0x4D, 0xC6, 0x6F, 0x65, 0x49, 0x34, 0x90, 0x67, 0x3A, 0xB3, 0x0D, 0xCA, 0x7C, 0x03, 0x1F, 0x0C, 0x21, 0x2C, 0x0D, 0x8B, 0xC9, 0xD0, 0xC8, 0x74, 0xB3, 0x19, 0xA9, 0x7A, 0xD1, + 0xCE, 0x93, 0x95, 0xD3, 0xD1, 0x54, 0x20, 0x31, 0x56, 0xC5, 0x1C, 0xC3, 0xB9, 0xCB, 0x13, 0xD0, 0xBA, 0x1B, 0xDF, 0x61, 0x8B, 0xC8, 0xEE, 0xCA, 0x9D, 0xDD, 0x94, 0x12, 0x05, 0x0C, 0xFA, 0x09, + 0x23, 0x57, 0x27, 0xAA, 0x50, 0xD4, 0x6F, 0x79, 0xAD, 0x6F, 0x3C, 0x5A, 0x1B, 0xB6, 0xB2, 0x84, 0xC8, 0x31, 0x1D, 0xCF, 0x93, 0x75, 0x68, 0x59, 0x70, 0x4D, 0xF8, 0xFC, 0x3B, 0xB8, 0xD2, 0xF5, + 0xE0, 0x94, 0xE0, 0x45, 0x02, 0x35, 0x49, 0x42, 0xE9, 0xC8, 0x52, 0xB2, 0x08, 0xD4, 0x90, 0x18, 0x34, 0x33, 0x2E, 0xBC, 0x60, 0x32, 0x70, 0xCB, 0x57, 0xED, 0x41, 0x8C, 0x34, 0xCE, 0x48, 0xAA, + }, + .pkcs8_len = 0, + .spki_len = 0, + .msg_len = 33, + .msg = { 0xD8, 0x1C, 0x4D, 0x8D, 0x73, 0x4F, 0xCB, 0xFB, 0xEA, 0xDE, 0x3D, 0x3F, 0x8A, 0x03, 0x9F, 0xAA, 0x2A, 0x2C, 0x99, 0x57, 0xE8, 0x35, 0xAD, 0x55, 0xB2, 0x2E, 0x75, 0xBF, 0x57, 0xBB, 0x55, 0x6A, + 0xC8 }, + .sig_len = 4595, + .sig = { + 0xBB, 0xF8, 0x5F, 0xFD, 0x0E, 0x01, 0xC8, 0x0C, 0x8C, 0x1C, 0x19, 0x31, 0xCD, 0x64, 0x0B, 0xF2, 0x73, 0xD4, 0x96, 0x93, 0xC4, 0xC4, 0xBF, 0xF5, 0xDD, 0x20, 0xD9, 0x4C, 0xF3, 0x75, 0x7A, 0xBD, + 0x45, 0x47, 0x3B, 0x9D, 0x01, 0xB1, 0x87, 0x13, 0x05, 0xDA, 0x90, 0xED, 0xC6, 0x70, 0x7D, 0x54, 0x17, 0x12, 0x94, 0x67, 0xF6, 0x1F, 0x72, 0x39, 0x50, 0xC1, 0xAE, 0xDF, 0x70, 0x55, 0xEC, 0x1D, + 0x47, 0x77, 0xAD, 0x88, 0x08, 0xE8, 0xB3, 0x47, 0xD1, 0xD0, 0x92, 0x1E, 0xBA, 0xB8, 0x90, 0xCC, 0xA8, 0xE3, 0xA0, 0xDF, 0xD3, 0x00, 0x3D, 0xE9, 0xF9, 0xCB, 0x4A, 0x97, 0xD8, 0x84, 0xE1, 0xDD, + 0x04, 0x2C, 0x95, 0x8B, 0x81, 0x6F, 0x72, 0x37, 0x03, 0x2B, 0x20, 0xF8, 0x39, 0x9A, 0x51, 0x82, 0xF4, 0x65, 0x25, 0xEC, 0x35, 0x7D, 0x2F, 0x03, 0x43, 0x74, 0x03, 0xE0, 0xCB, 0x5D, 0xCA, 0x4A, + 0x13, 0xFD, 0x2F, 0x1B, 0x09, 0x20, 0x5B, 0x98, 0x90, 0xF0, 0x2E, 0xE5, 0xAF, 0x54, 0x29, 0x43, 0xE6, 0xF9, 0x37, 0x5E, 0xD0, 0x8A, 0x38, 0x53, 0x30, 0x42, 0xD6, 0xBB, 0xD5, 0x0F, 0x37, 0x25, + 0x1B, 0x15, 0x90, 0xF6, 0x3B, 0x4B, 0x58, 0xA7, 0xD1, 0xE1, 0xF3, 0x1C, 0xE6, 0x2E, 0x3D, 0x2A, 0xA9, 0x1E, 0x1C, 0x76, 0x7B, 0x9C, 0x3F, 0x5C, 0xB2, 0x68, 0x23, 0xF9, 0x7A, 0xD1, 0xD9, 0xFF, + 0xAB, 0x28, 0x75, 0xEB, 0x68, 0xFF, 0xA9, 0xB0, 0x99, 0x46, 0xEF, 0x1D, 0x70, 0x12, 0xC0, 0x29, 0x19, 0xEF, 0x13, 0xCB, 0x10, 0x0C, 0x2E, 0x2C, 0x79, 0x87, 0xA0, 0xA5, 0x78, 0x5B, 0x5F, 0x3F, + 0x3B, 0x94, 0x8B, 0x7F, 0xD6, 0x4B, 0x85, 0xB1, 0x65, 0xAE, 0x2F, 0xBF, 0x3C, 0x47, 0xE0, 0x39, 0xC3, 0x07, 0x3C, 0xA7, 0x8F, 0xC9, 0x00, 0xBB, 0xCD, 0xC0, 0x69, 0xFE, 0x90, 0x68, 0x85, 0xD5, + 0xB1, 0x37, 0x40, 0xA2, 0x23, 0xAF, 0x52, 0x54, 0xF9, 0x8C, 0x1D, 0x58, 0xE2, 0xFC, 0x92, 0xB0, 0x37, 0x3E, 0x2A, 0x93, 0x33, 0x53, 0xCC, 0x3E, 0xEC, 0xD3, 0x9F, 0x71, 0xD5, 0x9C, 0xFA, 0x09, + 0x29, 0x4E, 0x38, 0x26, 0x2A, 0x44, 0x89, 0x40, 0x0D, 0x22, 0x29, 0x82, 0xF9, 0xC7, 0x80, 0xCD, 0x07, 0x31, 0xD4, 0xEE, 0xD9, 0x16, 0xC5, 0xA3, 0x1A, 0xBC, 0xD0, 0x2A, 0x59, 0x0E, 0xD8, 0xC6, + 0xFF, 0xE1, 0x8B, 0x5F, 0xC7, 0xB6, 0x88, 0x8E, 0x74, 0x72, 0x69, 0x40, 0xD0, 0x2C, 0xCC, 0x62, 0xD7, 0x8B, 0xCA, 0xED, 0xDA, 0x2E, 0x02, 0x8E, 0x53, 0x5C, 0xDA, 0xFC, 0x0E, 0x09, 0x1B, 0xEF, + 0x50, 0xDE, 0x2D, 0xFD, 0x12, 0x4F, 0x1E, 0x85, 0x4F, 0x56, 0x85, 0x27, 0xAE, 0xF4, 0xDC, 0x84, 0x55, 0xFD, 0xA0, 0x1B, 0x6D, 0x0D, 0x43, 0x04, 0x8E, 0xD5, 0xAB, 0x42, 0xB1, 0xD4, 0x08, 0x13, + 0x99, 0x4B, 0x9F, 0x6A, 0xA0, 0xC0, 0x36, 0xC0, 0xDC, 0xF0, 0x8F, 0x46, 0xB0, 0x0F, 0xDA, 0x01, 0x44, 0x77, 0xCF, 0x87, 0x9B, 0x8F, 0xE5, 0xEA, 0xC4, 0x54, 0x1B, 0x82, 0xDA, 0x00, 0xB4, 0x34, + 0x60, 0x46, 0x86, 0x5B, 0x09, 0x2E, 0xD6, 0xAE, 0x01, 0x15, 0xFC, 0x83, 0x4B, 0x58, 0xF7, 0x5F, 0xF9, 0x28, 0xD7, 0xD9, 0x9A, 0xC8, 0x69, 0x1F, 0xF7, 0x00, 0x20, 0xAB, 0xA2, 0x54, 0x80, 0xAB, + 0xBC, 0xC7, 0x09, 0xE4, 0x6E, 0xC5, 0x10, 0xF4, 0xB8, 0xCA, 0xDD, 0x60, 0x04, 0x59, 0x54, 0xD3, 0xED, 0xDA, 0x7C, 0x23, 0xE0, 0x3D, 0x91, 0x69, 0x4D, 0x3C, 0x3E, 0xA2, 0x92, 0xC9, 0x25, 0x35, + 0xE6, 0xB5, 0xFE, 0x17, 0x1C, 0x56, 0x7D, 0xF3, 0x72, 0x94, 0x06, 0xCD, 0xBA, 0x2A, 0x5E, 0xFA, 0x59, 0xF1, 0x56, 0xE9, 0xCC, 0xD0, 0x30, 0x2F, 0xDC, 0x0F, 0x8B, 0xB7, 0x59, 0xB0, 0x5D, 0xFF, + 0x5D, 0xD8, 0x02, 0xCE, 0x4D, 0x55, 0x06, 0xA1, 0x9A, 0x69, 0xD7, 0x0B, 0x3A, 0xB4, 0x8A, 0xB1, 0x7A, 0x2F, 0xE5, 0x95, 0x89, 0xF7, 0x30, 0x83, 0xCC, 0xA5, 0x47, 0xFF, 0xB3, 0xF1, 0x46, 0x83, + 0xC9, 0x14, 0xBC, 0x13, 0x45, 0xE7, 0x38, 0x7E, 0x83, 0x1E, 0xE6, 0x03, 0x75, 0x01, 0x49, 0x5C, 0x92, 0xC3, 0x57, 0x70, 0x5A, 0x69, 0xF9, 0x52, 0xA2, 0xF7, 0xCD, 0x30, 0xE0, 0x33, 0x36, 0xAF, + 0xAA, 0xFC, 0x9C, 0x56, 0x60, 0x4C, 0xD5, 0x45, 0xE8, 0x2A, 0xA1, 0x2A, 0xF0, 0x58, 0xDA, 0xBA, 0x97, 0x43, 0x87, 0xFE, 0x8D, 0xCD, 0xEC, 0x69, 0x9A, 0x1E, 0x38, 0x53, 0xE2, 0x6D, 0x29, 0xE1, + 0x57, 0x81, 0x89, 0xAA, 0x8C, 0x2B, 0xBA, 0x15, 0x50, 0xDF, 0xBE, 0xDD, 0x1E, 0x4F, 0x22, 0x4E, 0xFC, 0xD6, 0x54, 0x91, 0xE5, 0x4E, 0x56, 0x12, 0x8A, 0xE7, 0xC2, 0xDC, 0x85, 0x66, 0x79, 0x7A, + 0xBF, 0x2D, 0x94, 0x55, 0x91, 0x52, 0x03, 0xA5, 0xC8, 0x9E, 0x55, 0xDD, 0x23, 0xDF, 0x82, 0x74, 0x36, 0xA8, 0xD6, 0xDC, 0xC5, 0xAC, 0xA8, 0x2F, 0x9B, 0x18, 0x36, 0x92, 0x15, 0x9E, 0xC0, 0x3F, + 0x2B, 0x79, 0x8E, 0x55, 0x7D, 0x14, 0x73, 0x46, 0xD8, 0x35, 0xA8, 0xD8, 0x1B, 0x2E, 0x3D, 0x40, 0x86, 0x39, 0x66, 0x86, 0x3A, 0x54, 0xD9, 0xC8, 0x7B, 0x5A, 0xAC, 0xE9, 0x63, 0xCD, 0x52, 0x9A, + 0xDB, 0xAE, 0x07, 0x07, 0x0C, 0xEA, 0x00, 0xB7, 0x80, 0xE1, 0x81, 0x31, 0xE6, 0x4F, 0x0A, 0xD7, 0x0E, 0x91, 0x58, 0xF5, 0x90, 0xD0, 0x0A, 0xD9, 0x17, 0x79, 0x08, 0xB9, 0x03, 0x45, 0xFD, 0x79, + 0xD0, 0x25, 0x57, 0x71, 0xC6, 0x08, 0xAF, 0x65, 0xEE, 0x5A, 0xC3, 0xC5, 0x01, 0x66, 0xBA, 0xD0, 0x57, 0x38, 0x02, 0x58, 0x68, 0x19, 0x41, 0x56, 0x0F, 0x11, 0x33, 0x40, 0x5F, 0xC2, 0xD7, 0x61, + 0x13, 0x14, 0xB4, 0x38, 0x1D, 0x54, 0x59, 0xDC, 0xDE, 0xDE, 0x4D, 0x39, 0xF3, 0x82, 0x3B, 0xC4, 0x42, 0x2B, 0xB1, 0xD7, 0x36, 0xE7, 0x47, 0x4A, 0x80, 0x89, 0xF0, 0xEC, 0xFA, 0x3C, 0x30, 0xAA, + 0xC1, 0x19, 0xFF, 0xA4, 0x2B, 0xF7, 0x43, 0xF4, 0x8E, 0x0F, 0xDD, 0x96, 0x02, 0x92, 0xD3, 0xE4, 0x9A, 0x14, 0xEB, 0x05, 0x90, 0xC8, 0xE0, 0x2E, 0x42, 0x1D, 0x54, 0xAE, 0x8A, 0x52, 0x19, 0x51, + 0x5E, 0x21, 0x89, 0x59, 0x89, 0xA0, 0xD7, 0x1D, 0x4F, 0x45, 0x16, 0x69, 0xCD, 0x65, 0x2D, 0xA3, 0x48, 0x9E, 0x5C, 0xDB, 0xC0, 0x87, 0x6B, 0xA0, 0xA0, 0x89, 0x9E, 0x7D, 0x87, 0x73, 0xB2, 0x4A, + 0xFC, 0x2C, 0xD6, 0xD3, 0x7C, 0xA3, 0x80, 0xA5, 0xD0, 0xDD, 0x43, 0x63, 0x04, 0xD6, 0xE1, 0xA4, 0xDC, 0xD6, 0x38, 0xE8, 0xB9, 0x5E, 0x6C, 0x95, 0x46, 0x5C, 0x66, 0x90, 0xD4, 0xEF, 0xE8, 0xF4, + 0x46, 0x91, 0xE4, 0x8D, 0xE2, 0x2C, 0xFC, 0x69, 0x1C, 0x75, 0x61, 0xAD, 0x8C, 0xC1, 0xA2, 0xC3, 0xCC, 0x9F, 0xB8, 0x6F, 0xF6, 0xF4, 0x70, 0x5A, 0x57, 0x3A, 0x72, 0x04, 0x71, 0xED, 0x33, 0xA0, + 0x0E, 0x8A, 0x60, 0x20, 0x38, 0x18, 0xA3, 0x96, 0x1E, 0x4D, 0x21, 0x3A, 0x78, 0xB8, 0x62, 0x63, 0x94, 0xF7, 0x5C, 0x28, 0x23, 0x15, 0x57, 0x4C, 0xCD, 0x72, 0x5A, 0x67, 0xE2, 0x0F, 0x0B, 0xF2, + 0x24, 0xBF, 0xFC, 0xAB, 0xD7, 0x02, 0xBF, 0xD4, 0xE1, 0xCC, 0x5F, 0x78, 0xBE, 0xC0, 0xE0, 0x42, 0xE1, 0x2E, 0xD4, 0xC9, 0x47, 0x4B, 0xDD, 0x5E, 0xED, 0x2A, 0xEB, 0x53, 0xF4, 0xA9, 0x58, 0xD7, + 0xF8, 0x4E, 0xFD, 0x56, 0xEC, 0x03, 0x0A, 0x94, 0xD2, 0x00, 0xA5, 0x39, 0xDE, 0x16, 0x4E, 0x53, 0xC8, 0x2A, 0xFE, 0x8C, 0x5F, 0x71, 0xBB, 0x99, 0xA0, 0x1F, 0x72, 0x30, 0xB7, 0xAE, 0xBC, 0x21, + 0x3E, 0xCD, 0xDB, 0xEF, 0x5B, 0x9E, 0x90, 0x64, 0x87, 0x43, 0x96, 0xF8, 0xA9, 0x1B, 0x05, 0x75, 0xF6, 0x8A, 0x45, 0x15, 0xDD, 0x15, 0x81, 0x78, 0xBF, 0x27, 0x7A, 0x90, 0xA3, 0xFE, 0xA2, 0x00, + 0x92, 0x00, 0xDA, 0x2E, 0xDA, 0x2C, 0x8B, 0x3A, 0x47, 0xC1, 0x04, 0xD3, 0x50, 0xDF, 0x68, 0xE9, 0x4C, 0x8A, 0x40, 0x23, 0xD3, 0xAE, 0xFB, 0xB7, 0x07, 0x18, 0xFA, 0x2E, 0x27, 0xE6, 0xA5, 0xC3, + 0xF9, 0x92, 0x7E, 0xC5, 0x96, 0xAB, 0x54, 0x0F, 0x46, 0x3A, 0xE0, 0x10, 0xEF, 0x71, 0xB8, 0x9B, 0x49, 0x49, 0x7F, 0x0C, 0xFD, 0x29, 0x39, 0xFF, 0xAB, 0x2A, 0x7D, 0xD1, 0x24, 0x7D, 0xC4, 0xA5, + 0x9D, 0x84, 0x11, 0xA8, 0x43, 0xBD, 0x84, 0xF1, 0xEA, 0x8D, 0xA3, 0x3C, 0x07, 0x01, 0xD7, 0x0A, 0xC2, 0x7C, 0x4B, 0xDB, 0xD0, 0xD9, 0xA0, 0xCA, 0xB8, 0x6B, 0x1F, 0xC5, 0xBE, 0x12, 0x45, 0x8A, + 0x25, 0x80, 0xA6, 0xCA, 0xB4, 0xB7, 0x65, 0xB8, 0x42, 0xC6, 0x7A, 0xD5, 0x4C, 0xA5, 0xD4, 0x0A, 0x24, 0xE2, 0xDD, 0xBC, 0xF0, 0x1E, 0x46, 0x6E, 0x08, 0xD9, 0xB3, 0x44, 0x9F, 0x13, 0xE8, 0x2E, + 0x16, 0xD6, 0x1C, 0x72, 0x3F, 0xB9, 0x46, 0x2E, 0x97, 0xB7, 0xAB, 0xC7, 0x0B, 0x22, 0x10, 0xEC, 0xA1, 0x6B, 0x16, 0x0D, 0x5B, 0x8F, 0x98, 0xA1, 0x79, 0x4D, 0xCA, 0x92, 0xCD, 0x4F, 0x02, 0x7F, + 0x3E, 0x41, 0x52, 0xEA, 0x87, 0x95, 0x07, 0xDD, 0xFE, 0x7F, 0x1F, 0x21, 0x51, 0x41, 0x53, 0xF0, 0x36, 0xAA, 0xBC, 0x33, 0xF1, 0x72, 0xC9, 0x5A, 0x9B, 0x77, 0x47, 0x22, 0x80, 0x0F, 0x2E, 0x08, + 0xCC, 0x44, 0xF9, 0x23, 0x54, 0x0D, 0x8A, 0xF6, 0x4B, 0x42, 0x99, 0x68, 0xB2, 0x80, 0x36, 0x4C, 0x1B, 0x7B, 0x4B, 0x3E, 0x9B, 0xEE, 0x40, 0xC5, 0x00, 0x02, 0x65, 0x7D, 0x99, 0x46, 0x31, 0xF3, + 0x3A, 0x8F, 0x8F, 0x13, 0x4A, 0x27, 0xEB, 0x69, 0xBA, 0x43, 0x95, 0x90, 0x8B, 0xA4, 0x06, 0x34, 0xB8, 0xF2, 0x70, 0x31, 0x49, 0x27, 0x5F, 0xFB, 0xBE, 0x8B, 0x48, 0x3E, 0xA1, 0xBB, 0xA9, 0x1C, + 0x28, 0x10, 0x51, 0x36, 0xD9, 0x7C, 0x47, 0x0E, 0xE8, 0x3C, 0xD2, 0x1C, 0xEB, 0x2B, 0x21, 0xAA, 0xED, 0x98, 0xDB, 0x8A, 0xB1, 0x65, 0xA7, 0xB4, 0xBE, 0x55, 0x9E, 0x7E, 0xAC, 0xA6, 0x84, 0x60, + 0x30, 0x15, 0xBC, 0x34, 0x9B, 0x0A, 0x51, 0x21, 0x4E, 0x4E, 0x8F, 0xBE, 0x1D, 0x2D, 0x88, 0x3F, 0x79, 0xFD, 0x3F, 0x1E, 0xDC, 0xDD, 0x3F, 0xA6, 0xD4, 0xB5, 0xBB, 0xD2, 0xA5, 0xB3, 0x00, 0x3A, + 0x80, 0xF1, 0xDA, 0xDE, 0x97, 0x5B, 0x50, 0x2C, 0x7F, 0x72, 0x03, 0x73, 0x16, 0xBC, 0x55, 0xC1, 0xE5, 0x7E, 0x50, 0x06, 0x27, 0xD6, 0x0E, 0x31, 0x08, 0x74, 0x31, 0xD2, 0xC9, 0xD0, 0x2C, 0xA9, + 0xF0, 0xEB, 0xCC, 0xD4, 0xBF, 0xE3, 0xC4, 0xBB, 0x53, 0x6D, 0x4C, 0xFE, 0xF7, 0x51, 0x07, 0x50, 0x45, 0x2D, 0x44, 0x4B, 0xE2, 0xC3, 0xD6, 0x4D, 0x84, 0xA8, 0x32, 0x96, 0x53, 0x05, 0x26, 0x4A, + 0xBB, 0x53, 0xE3, 0x61, 0x49, 0x40, 0xF9, 0xB2, 0xF1, 0xEA, 0x6F, 0x41, 0xCA, 0x8F, 0x69, 0xE7, 0x26, 0x69, 0x0B, 0xA6, 0x30, 0x63, 0x0F, 0x8A, 0x91, 0x6E, 0xE8, 0x56, 0x26, 0x82, 0x51, 0xB7, + 0x73, 0xDC, 0x2A, 0x5D, 0xB4, 0x5D, 0x22, 0xDF, 0xB2, 0x43, 0x9C, 0xA4, 0xB7, 0xAB, 0x70, 0x21, 0x5D, 0x23, 0xE1, 0xF2, 0xE2, 0x61, 0x73, 0x94, 0xFF, 0x78, 0x3B, 0x0B, 0xFF, 0x6D, 0xF0, 0x34, + 0x5C, 0xC9, 0x27, 0x05, 0x3D, 0x02, 0xC6, 0x5F, 0xE2, 0xA8, 0x6D, 0xEF, 0xBE, 0xBF, 0x52, 0x43, 0xA2, 0xEF, 0x6A, 0x63, 0x12, 0xBA, 0xED, 0xB6, 0xE6, 0x0D, 0xBB, 0x0C, 0x67, 0xCC, 0x9A, 0x65, + 0x55, 0x85, 0xCB, 0x45, 0x8D, 0x6A, 0x04, 0x18, 0x11, 0x94, 0x81, 0x5F, 0x03, 0xBE, 0x87, 0xF6, 0xE8, 0x00, 0x49, 0x2A, 0x24, 0xC5, 0xD5, 0x02, 0xD5, 0xEC, 0xD5, 0x3D, 0xD6, 0xDA, 0x36, 0x79, + 0x95, 0xD3, 0x2E, 0x8B, 0xBA, 0xA3, 0xEF, 0x62, 0x72, 0x7E, 0x8A, 0x61, 0x0E, 0x8D, 0x6B, 0x5C, 0x8F, 0xAB, 0xCB, 0xE8, 0x89, 0x3B, 0xDB, 0x5E, 0x03, 0x86, 0x27, 0xF7, 0x07, 0xE8, 0x46, 0x4C, + 0x55, 0xDC, 0xBB, 0x76, 0xF0, 0x83, 0x6A, 0xDD, 0x29, 0x8A, 0x96, 0x7C, 0x45, 0x95, 0x08, 0xBC, 0x4E, 0x88, 0xBA, 0x5C, 0xA3, 0x8F, 0x5A, 0x56, 0x1A, 0x6D, 0x2D, 0x6C, 0xB2, 0x17, 0x8D, 0x90, + 0xAC, 0x85, 0x0C, 0xA2, 0x73, 0x4B, 0x45, 0xC4, 0xA8, 0x9A, 0xA0, 0xF1, 0x52, 0xA3, 0xB5, 0x3B, 0xCF, 0x1E, 0x13, 0x53, 0x2B, 0x2B, 0x5B, 0x38, 0x78, 0xB2, 0x05, 0xBD, 0x2B, 0x32, 0x7D, 0xC4, + 0x9E, 0xB6, 0x66, 0x0B, 0x95, 0x11, 0xBF, 0xAE, 0x90, 0xC1, 0xDE, 0xA5, 0xBD, 0xEB, 0x6D, 0xC5, 0xDA, 0x06, 0x8B, 0xCB, 0xDC, 0x6C, 0x09, 0x3E, 0x57, 0x27, 0xE3, 0x87, 0x37, 0x4F, 0x45, 0x2F, + 0x96, 0x3C, 0x30, 0x7D, 0xEE, 0x86, 0x5D, 0x41, 0xAA, 0x12, 0x4C, 0xA8, 0x03, 0xC1, 0x2F, 0x9A, 0xE9, 0x29, 0x9C, 0x3C, 0xB1, 0x34, 0x5F, 0xCC, 0x56, 0x8C, 0x6E, 0x71, 0xBE, 0x33, 0x66, 0xBF, + 0x30, 0xEF, 0xEE, 0xEF, 0xC7, 0x69, 0x3C, 0x36, 0xAC, 0xE5, 0x76, 0xB0, 0xD1, 0x0F, 0x40, 0x2F, 0x38, 0x00, 0x09, 0xFD, 0x0E, 0xC0, 0x68, 0xCB, 0x2D, 0x45, 0x98, 0x48, 0x84, 0xED, 0xF1, 0x6B, + 0xC9, 0x0B, 0x0F, 0xF6, 0xDC, 0x96, 0x30, 0x9E, 0xA3, 0x77, 0xA3, 0xCE, 0xC0, 0x43, 0xCB, 0x76, 0xB6, 0xC8, 0x85, 0xBB, 0xB8, 0x48, 0xC4, 0x74, 0x5B, 0x71, 0xE1, 0x8C, 0x58, 0xE7, 0x80, 0x50, + 0xE1, 0x9B, 0xD7, 0xBE, 0x08, 0x31, 0xEF, 0xE9, 0x05, 0x2A, 0x6A, 0x7D, 0xF8, 0xD4, 0xE8, 0xB9, 0xFC, 0x3E, 0x08, 0x2A, 0x4D, 0x40, 0xAD, 0x73, 0xE4, 0xB3, 0x18, 0x5E, 0x2F, 0x6D, 0xED, 0xE7, + 0xEE, 0x51, 0xA4, 0x06, 0x8F, 0xF2, 0xDA, 0x57, 0x37, 0x3F, 0xD7, 0xE7, 0xBD, 0x46, 0xE0, 0x08, 0x0F, 0x4C, 0x2C, 0x1F, 0x41, 0xBC, 0x25, 0x0E, 0x6D, 0xA4, 0x5A, 0x34, 0x1F, 0x21, 0x47, 0x71, + 0xF5, 0x53, 0x1A, 0x67, 0xB0, 0xFD, 0x97, 0xB5, 0x3C, 0xD7, 0x2C, 0xFA, 0xC7, 0x21, 0x5B, 0xC4, 0x11, 0x1F, 0x09, 0x40, 0x30, 0xA9, 0x13, 0x83, 0xD2, 0x01, 0x82, 0x21, 0x0F, 0xCE, 0xCD, 0x75, + 0xE5, 0x9C, 0x4B, 0x0B, 0x33, 0xA3, 0xF9, 0x3D, 0x86, 0x5D, 0x84, 0x7E, 0xC2, 0x41, 0xE1, 0xB9, 0x84, 0x81, 0xC5, 0xD9, 0xD2, 0x7F, 0x0A, 0xE2, 0x62, 0xB3, 0x28, 0x65, 0x0C, 0xDC, 0x13, 0xCD, + 0x99, 0x86, 0x6B, 0xE9, 0xA5, 0xA0, 0x30, 0xE8, 0x3D, 0x84, 0xE3, 0x2B, 0xD2, 0x13, 0xC9, 0x4B, 0xD6, 0xAF, 0x95, 0x04, 0x33, 0xA4, 0xF0, 0x0C, 0x61, 0x49, 0x78, 0x3B, 0x00, 0x75, 0x0C, 0xDF, + 0xD4, 0xF4, 0x7A, 0xE7, 0x52, 0x17, 0xEE, 0xD1, 0xF6, 0x0C, 0x36, 0x6F, 0xA0, 0x2C, 0xDB, 0x20, 0x6F, 0xEB, 0x2A, 0x68, 0x5D, 0x6B, 0x7D, 0x6A, 0x4C, 0x13, 0x55, 0x3E, 0x2B, 0xE2, 0x77, 0x94, + 0xF5, 0x3B, 0x0E, 0xF5, 0x73, 0x15, 0x20, 0x32, 0x63, 0xEB, 0x02, 0x6E, 0xA5, 0xE6, 0x70, 0x67, 0xD2, 0x2F, 0x92, 0xE2, 0x6E, 0x98, 0xDF, 0x9A, 0xB3, 0x86, 0xC2, 0x70, 0x5B, 0x43, 0x16, 0xA6, + 0x98, 0x92, 0x68, 0x8E, 0x60, 0x1E, 0x74, 0x27, 0x59, 0x5A, 0xCE, 0xE6, 0xE4, 0x7F, 0x5E, 0xC5, 0x98, 0xCC, 0x48, 0xC2, 0xF2, 0xDA, 0x1C, 0x32, 0xE0, 0x62, 0xA3, 0x49, 0xD8, 0x9D, 0xCC, 0x8C, + 0x05, 0xC6, 0x2E, 0x7B, 0x0C, 0xED, 0x6F, 0x2E, 0x93, 0xA7, 0xBD, 0x48, 0xA8, 0x00, 0x4A, 0x8C, 0x5C, 0x60, 0x5D, 0xFF, 0xC8, 0x05, 0xDE, 0x07, 0x9E, 0xDE, 0xE7, 0xCE, 0xD9, 0x86, 0x39, 0xA9, + 0x2F, 0x6C, 0xBA, 0x92, 0xF2, 0x08, 0x9B, 0x14, 0x5D, 0x2D, 0x61, 0xD9, 0x63, 0x8C, 0x07, 0x34, 0x7A, 0x2E, 0xF6, 0xB3, 0x0F, 0xD9, 0x0E, 0x11, 0x1A, 0x7F, 0x59, 0x13, 0xF6, 0xE1, 0x87, 0x95, + 0xC1, 0x9E, 0x0B, 0x9F, 0x60, 0xF8, 0x5B, 0xD8, 0xF5, 0xC9, 0xA9, 0x63, 0x33, 0x94, 0x41, 0xE4, 0xA5, 0xB7, 0x9E, 0xB2, 0xE8, 0x67, 0x96, 0x1B, 0x18, 0xA1, 0x88, 0x4A, 0x01, 0xA7, 0x44, 0x83, + 0xD8, 0x0B, 0x40, 0x3E, 0xFB, 0xDB, 0xD4, 0xED, 0xDD, 0xC1, 0x92, 0x2D, 0xA3, 0xFB, 0xB3, 0x7B, 0xEA, 0x97, 0xE0, 0xA5, 0xB6, 0x34, 0x3E, 0x43, 0x67, 0x60, 0x1B, 0xD2, 0x1D, 0xB6, 0x69, 0x41, + 0xC2, 0x69, 0x8B, 0xF5, 0x06, 0xB0, 0x48, 0x61, 0xB5, 0xF3, 0xD3, 0xD8, 0x0A, 0xC6, 0xDC, 0xB6, 0x84, 0xD9, 0xC4, 0x36, 0x9A, 0xBD, 0x04, 0xBC, 0x4B, 0xDB, 0xEF, 0x49, 0xC6, 0x6E, 0x38, 0x44, + 0x51, 0x3A, 0x3F, 0x3B, 0xDD, 0x40, 0x0C, 0x08, 0x0A, 0xC6, 0xEA, 0xD8, 0x1E, 0x8B, 0xB0, 0xE7, 0xCB, 0x36, 0xDB, 0x7B, 0x7E, 0xAB, 0x47, 0x28, 0x39, 0x18, 0x57, 0xF5, 0x97, 0xA3, 0x46, 0x48, + 0x63, 0xC3, 0x12, 0x64, 0x5B, 0x20, 0xAF, 0x02, 0xF7, 0xD0, 0xBD, 0x9A, 0x74, 0xDE, 0x23, 0x61, 0xA0, 0xD2, 0xD9, 0x8A, 0x69, 0x89, 0x75, 0xB3, 0x0F, 0x10, 0x10, 0xD9, 0x0A, 0x12, 0x60, 0x78, + 0x58, 0x4A, 0x45, 0xFF, 0xBC, 0xC6, 0x5B, 0x47, 0x97, 0x6A, 0xF6, 0x57, 0xEA, 0x84, 0xE9, 0x73, 0x0D, 0x9E, 0x36, 0x37, 0x33, 0x73, 0x6A, 0xC8, 0x01, 0x03, 0xDC, 0x1C, 0x75, 0x73, 0xC4, 0xDE, + 0xE2, 0x8A, 0x7B, 0xAC, 0x9E, 0xF7, 0x2C, 0xB8, 0x29, 0x45, 0x0B, 0x53, 0xEA, 0xF9, 0x84, 0xCD, 0x01, 0xAA, 0x31, 0x41, 0x6C, 0xE8, 0x91, 0x4B, 0x7D, 0x7E, 0xF8, 0x49, 0xEB, 0x9C, 0xC1, 0x72, + 0xD7, 0x09, 0x6D, 0xEF, 0xDA, 0xCF, 0x59, 0x6B, 0x9B, 0x21, 0xA5, 0x73, 0xE3, 0x46, 0xA4, 0x7A, 0x5A, 0x46, 0x9E, 0x1D, 0x79, 0x39, 0xBE, 0x19, 0x82, 0xCB, 0x39, 0x54, 0xC2, 0x14, 0xED, 0x3A, + 0x37, 0x07, 0xD7, 0x40, 0xC0, 0x33, 0xE3, 0xEF, 0x78, 0x0F, 0x4C, 0x48, 0xBA, 0xDD, 0x86, 0x38, 0x48, 0xBB, 0xFC, 0x9D, 0xAA, 0x8E, 0x38, 0x06, 0xA8, 0x4B, 0x2C, 0xAC, 0x0C, 0xA2, 0x32, 0x00, + 0x0C, 0xAF, 0x02, 0x03, 0xE9, 0x08, 0xFC, 0xE1, 0x8B, 0x5D, 0x62, 0x77, 0x72, 0x25, 0xD2, 0xD7, 0xD5, 0x84, 0xF2, 0xED, 0x71, 0x88, 0x5D, 0xFA, 0xF5, 0xA4, 0xDB, 0xEE, 0x02, 0xF2, 0x85, 0xBC, + 0x34, 0x55, 0x9B, 0x88, 0xEA, 0x9C, 0xE1, 0x5B, 0x47, 0xA3, 0xB9, 0x2A, 0x8D, 0x6F, 0x91, 0x59, 0x1C, 0x32, 0x9A, 0x5A, 0xA2, 0x1A, 0x1B, 0xC4, 0x24, 0xBA, 0x2B, 0xDB, 0xD1, 0x64, 0xCE, 0x1A, + 0x8B, 0x78, 0xB3, 0x8B, 0xEF, 0x2B, 0x47, 0xF2, 0x1F, 0x7F, 0xB7, 0xA3, 0xC5, 0x4E, 0x3E, 0xA4, 0x53, 0x6E, 0x81, 0x6E, 0x01, 0x65, 0x6C, 0x8E, 0x26, 0xAD, 0x42, 0xF3, 0xCB, 0x90, 0x61, 0x69, + 0x67, 0xC0, 0xDD, 0x07, 0x9F, 0x95, 0x6C, 0x9F, 0x3C, 0x84, 0x4D, 0x5F, 0x33, 0x9C, 0x62, 0xEE, 0x8A, 0x35, 0x8C, 0x4B, 0xEC, 0x2D, 0x27, 0x8A, 0xF7, 0x18, 0xAD, 0x50, 0x9C, 0x6B, 0x66, 0x61, + 0x3B, 0x58, 0x04, 0x43, 0xFA, 0x6F, 0x11, 0xCD, 0x8D, 0x10, 0x76, 0x93, 0xB5, 0xD7, 0xB7, 0x38, 0xAA, 0x7E, 0x2F, 0xE6, 0x62, 0x50, 0x2D, 0x75, 0x04, 0xA9, 0xF5, 0x96, 0x19, 0x41, 0x80, 0xF8, + 0x70, 0x0D, 0xC4, 0xE6, 0xF7, 0xE8, 0xE7, 0xD2, 0x30, 0x72, 0x34, 0x49, 0x4B, 0x8D, 0xF1, 0xD5, 0x7E, 0xE1, 0x4D, 0x6C, 0x97, 0x92, 0x6E, 0xB1, 0xD8, 0x90, 0x4D, 0x80, 0x89, 0xBE, 0x7D, 0x13, + 0x5B, 0x13, 0xD6, 0xDE, 0x30, 0xAA, 0x87, 0x20, 0xD6, 0x71, 0x59, 0xBB, 0x50, 0xA8, 0x34, 0xDE, 0x90, 0x79, 0x92, 0x2B, 0x88, 0x93, 0x1D, 0x45, 0x85, 0x00, 0x62, 0x68, 0x34, 0xDA, 0x04, 0x0D, + 0xB7, 0x68, 0xDD, 0xDB, 0xE6, 0x7A, 0x75, 0x8A, 0x02, 0xB4, 0x48, 0xE3, 0x6B, 0xA4, 0x55, 0x03, 0x4A, 0xDE, 0x36, 0x80, 0x2A, 0xA4, 0x2A, 0x7F, 0x2F, 0x23, 0x4A, 0x5E, 0x1C, 0xC2, 0x41, 0xE5, + 0x66, 0x1C, 0x63, 0xAF, 0xCE, 0x59, 0xDF, 0xDC, 0xC0, 0x89, 0x83, 0x47, 0xD2, 0x83, 0x4D, 0x72, 0x64, 0xF5, 0xB2, 0x1A, 0x47, 0xC5, 0x21, 0x4A, 0xDC, 0x57, 0xAF, 0x76, 0xCE, 0x9E, 0xBD, 0xB6, + 0x8C, 0x71, 0x02, 0x9B, 0xCF, 0x0C, 0x4C, 0x74, 0x5A, 0x33, 0x45, 0x4A, 0xCF, 0x0C, 0xF6, 0xD5, 0xC6, 0x8D, 0xEA, 0x06, 0xC4, 0x5E, 0x7D, 0x4D, 0x17, 0x55, 0xC5, 0xAC, 0xDC, 0x37, 0xFC, 0x24, + 0x34, 0x14, 0x0E, 0xF7, 0x07, 0xFD, 0x55, 0xFA, 0xF0, 0x6C, 0xBB, 0x17, 0x07, 0xC2, 0x7C, 0xE9, 0xD9, 0x05, 0x90, 0x5E, 0x37, 0xE2, 0xF1, 0x47, 0xC9, 0xCB, 0x88, 0x08, 0xEC, 0xD0, 0x5D, 0xF7, + 0x1F, 0xC5, 0xF1, 0xDA, 0xF9, 0x10, 0xD7, 0xBD, 0x68, 0xB6, 0x91, 0x49, 0x38, 0xBF, 0x0C, 0xAB, 0xCF, 0x66, 0xC9, 0x05, 0xC4, 0x95, 0x63, 0xD7, 0xD7, 0x0F, 0x2C, 0x3D, 0x3A, 0x4A, 0x4F, 0x62, + 0x9E, 0x3A, 0xFD, 0xE5, 0x3B, 0xD1, 0x4C, 0xD6, 0xE5, 0x27, 0xE4, 0xF0, 0x38, 0xD6, 0xA3, 0x31, 0xD0, 0x14, 0x68, 0xE2, 0x2D, 0xFE, 0x93, 0xA3, 0x79, 0xB3, 0xEC, 0x6D, 0xA6, 0xD1, 0xC2, 0xF6, + 0xD5, 0xEA, 0xB1, 0x41, 0xE5, 0x75, 0xF9, 0x3C, 0x8C, 0xC5, 0x58, 0x0D, 0xF4, 0xA3, 0xDB, 0x5C, 0x4C, 0x87, 0xD8, 0x54, 0x8E, 0x9A, 0x85, 0x19, 0x46, 0xD1, 0xB9, 0x0D, 0x75, 0x27, 0x40, 0x7F, + 0x1B, 0xA1, 0x12, 0x1E, 0xAC, 0x54, 0xA1, 0x1E, 0x6E, 0xDA, 0x45, 0xAB, 0xB0, 0x8A, 0x7A, 0x78, 0xAB, 0x36, 0xA7, 0x6E, 0xAD, 0x7F, 0xAC, 0x46, 0x78, 0xE5, 0x24, 0x64, 0xEF, 0xF3, 0x98, 0xE9, + 0x02, 0x15, 0xAC, 0x31, 0x6D, 0xE5, 0xA6, 0xEF, 0xE5, 0xA7, 0xB4, 0xA9, 0x5D, 0xF9, 0x2E, 0x41, 0x29, 0xF3, 0xF9, 0x1B, 0x31, 0x6F, 0x75, 0x67, 0x08, 0xBD, 0xF3, 0x7C, 0x01, 0xC1, 0x2B, 0xBA, + 0xA0, 0x91, 0xF9, 0x48, 0x84, 0xE3, 0x8A, 0xFF, 0x3C, 0x7B, 0x81, 0x40, 0x88, 0x8C, 0xAB, 0x4F, 0x7F, 0x86, 0x7E, 0xAD, 0xB0, 0x41, 0x85, 0x84, 0xB6, 0xF7, 0x70, 0x74, 0x02, 0x50, 0x93, 0x6A, + 0x13, 0x8A, 0xFF, 0x52, 0x88, 0x88, 0x40, 0x67, 0x7D, 0x81, 0x21, 0xC5, 0x83, 0x80, 0x6F, 0xE2, 0x71, 0x04, 0xDE, 0x52, 0x88, 0x13, 0xE5, 0x62, 0x26, 0xB6, 0x52, 0xC5, 0x86, 0x9B, 0xB5, 0x00, + 0x30, 0x38, 0x34, 0xD9, 0xC9, 0xD1, 0x97, 0xDB, 0xA1, 0xDD, 0x5C, 0x47, 0x34, 0x30, 0x7A, 0xB8, 0xBD, 0x00, 0x6B, 0x66, 0xEF, 0x45, 0xAB, 0xED, 0x2E, 0x31, 0x37, 0x7B, 0xEA, 0xA1, 0x9D, 0xAE, + 0x6E, 0xC8, 0x2A, 0xD7, 0x7C, 0x4C, 0x07, 0x74, 0x4F, 0x9B, 0x93, 0xA8, 0xDD, 0x4C, 0xEE, 0x1A, 0x62, 0xA5, 0x52, 0xED, 0xF4, 0xE2, 0x77, 0xCA, 0xCF, 0xF1, 0xF9, 0x64, 0xDA, 0x7A, 0xF8, 0xFA, + 0xFF, 0x6B, 0x56, 0xE3, 0xEB, 0xC0, 0x68, 0x50, 0xA9, 0xF7, 0x6E, 0xCF, 0xB2, 0xC2, 0xBA, 0xA6, 0x60, 0x95, 0x8C, 0x6D, 0x1B, 0xA9, 0x6B, 0xA8, 0x57, 0x8D, 0x06, 0x6D, 0x6A, 0xFE, 0x6E, 0x8F, + 0xB2, 0x05, 0x2B, 0x74, 0x21, 0xD5, 0x7D, 0xE5, 0xAB, 0x4C, 0x1F, 0xD5, 0x51, 0x70, 0xE9, 0xEE, 0x33, 0xEB, 0x32, 0xFB, 0x3D, 0x2C, 0x88, 0x61, 0x42, 0x05, 0x5E, 0xE8, 0x42, 0x8B, 0xD7, 0x45, + 0xAA, 0xBE, 0x1D, 0x15, 0x19, 0x1F, 0xFC, 0x93, 0xA3, 0xFA, 0x7A, 0x86, 0xB4, 0x27, 0xEB, 0x23, 0x70, 0xB7, 0x8A, 0x67, 0xA4, 0x85, 0xAF, 0x96, 0x3B, 0xBE, 0x1F, 0x22, 0x46, 0x11, 0x9F, 0xB4, + 0x69, 0xA0, 0x02, 0xD7, 0x02, 0x9F, 0xC4, 0xF5, 0xF7, 0xE0, 0x12, 0x5F, 0xDA, 0x73, 0x05, 0xAC, 0xF6, 0xC8, 0x0C, 0x7B, 0xD3, 0xF6, 0x68, 0x89, 0x7B, 0xA8, 0x14, 0x35, 0xF4, 0x26, 0xB8, 0x42, + 0x5C, 0x98, 0x55, 0xCD, 0x46, 0xC3, 0x44, 0x8B, 0xBA, 0xD0, 0x73, 0x9B, 0xA8, 0x8A, 0xBC, 0x27, 0x3B, 0xCD, 0x0F, 0xA1, 0xFD, 0xA7, 0xF4, 0xF8, 0x18, 0x3B, 0x5D, 0x73, 0xD1, 0x6C, 0x40, 0x7C, + 0x45, 0x2A, 0xEF, 0xA2, 0xE3, 0xCA, 0x9F, 0x2D, 0x9D, 0x63, 0x8D, 0x96, 0x6A, 0x58, 0x78, 0x8B, 0x48, 0xBF, 0xC5, 0x7D, 0x3F, 0xC2, 0x08, 0x5F, 0xE8, 0x5A, 0x7F, 0x7A, 0xDD, 0xD9, 0x1E, 0xFD, + 0x1B, 0xA0, 0x22, 0x60, 0x46, 0xB1, 0x27, 0xA9, 0x7B, 0xC4, 0x80, 0x47, 0x9B, 0x92, 0x88, 0x1A, 0x58, 0xA0, 0xBC, 0x04, 0xD8, 0xDD, 0x9E, 0x68, 0xB6, 0xD2, 0xBC, 0x50, 0x34, 0xCF, 0x23, 0x43, + 0x0D, 0x1F, 0xE5, 0x49, 0x91, 0xA6, 0x90, 0x8B, 0x01, 0x9E, 0xE0, 0x18, 0xC8, 0x43, 0xB9, 0xFA, 0x53, 0xEC, 0x7E, 0xE5, 0xF1, 0x14, 0xAB, 0xE2, 0xB7, 0x50, 0xD4, 0xE1, 0xE7, 0x2E, 0xAF, 0xB4, + 0xFB, 0xB3, 0x3A, 0x1E, 0x2C, 0x4D, 0x62, 0x72, 0xCE, 0xE2, 0x7B, 0xBB, 0x13, 0xB5, 0xD2, 0x3E, 0x24, 0xF6, 0x12, 0x9C, 0xF5, 0x82, 0x5F, 0x34, 0xAF, 0xC0, 0x56, 0xF9, 0x5F, 0x53, 0xA0, 0x9F, + 0x6F, 0xCA, 0x94, 0x35, 0xCD, 0x5F, 0xB6, 0xC0, 0x5F, 0x88, 0xB4, 0xDC, 0xE8, 0x6C, 0xEA, 0xBD, 0x7E, 0x0C, 0x78, 0x53, 0x61, 0xD2, 0x53, 0xBB, 0x9C, 0xDB, 0x3A, 0x0C, 0x6B, 0xC8, 0x51, 0x83, + 0x01, 0xFF, 0x44, 0xF9, 0xE8, 0x7F, 0x7A, 0x97, 0xEC, 0x9F, 0x02, 0xFA, 0xB5, 0x13, 0x4F, 0x3B, 0xBF, 0xA1, 0xCB, 0xE4, 0x4F, 0xA8, 0x3F, 0x1C, 0x54, 0x3E, 0xD9, 0xB8, 0x70, 0x65, 0x75, 0x43, + 0x5A, 0xC6, 0xA1, 0x5F, 0x7B, 0x0D, 0xEB, 0xA9, 0xD4, 0x5A, 0xF5, 0x54, 0xBB, 0x0C, 0xCB, 0xCA, 0x12, 0xA6, 0xC1, 0x6E, 0x5E, 0xE6, 0xFA, 0xD6, 0x37, 0x21, 0xE4, 0xC3, 0xCC, 0x8D, 0x9E, 0xA6, + 0x8C, 0x61, 0x49, 0x99, 0x30, 0x80, 0x95, 0x24, 0x07, 0xAF, 0xA2, 0x03, 0xF5, 0x04, 0xA8, 0x87, 0xB3, 0xBF, 0x84, 0xD2, 0xBB, 0x6E, 0x45, 0xE7, 0xCC, 0x53, 0x26, 0x53, 0x3D, 0x63, 0x96, 0x3F, + 0xFB, 0x72, 0xA9, 0x27, 0x2C, 0x8F, 0xF6, 0x37, 0xBE, 0x6E, 0x24, 0x73, 0xE9, 0xFC, 0xAB, 0x6B, 0x5E, 0x5E, 0x7C, 0xF3, 0xED, 0xBD, 0xDA, 0xEF, 0x51, 0xC9, 0x8D, 0x53, 0x17, 0x0F, 0x9B, 0x64, + 0xBC, 0xA5, 0xD4, 0x9F, 0x76, 0xAF, 0x17, 0x6D, 0x01, 0xA6, 0xF2, 0xEC, 0xB3, 0x39, 0x15, 0x1F, 0x49, 0xE4, 0x9A, 0x8F, 0x6E, 0x28, 0x6C, 0x6D, 0x41, 0x22, 0xD6, 0x50, 0xD5, 0x01, 0x59, 0x10, + 0xFF, 0x7F, 0x28, 0x02, 0x46, 0x93, 0x89, 0x5C, 0x58, 0x03, 0xDD, 0xFF, 0xCB, 0x1E, 0xDC, 0x46, 0x79, 0xC8, 0xF5, 0x35, 0xAC, 0x15, 0x97, 0xD9, 0xB2, 0x8A, 0xC4, 0x6E, 0x62, 0x88, 0x81, 0x01, + 0x29, 0xC1, 0x79, 0x55, 0x6A, 0xF7, 0x88, 0x2D, 0xEE, 0x17, 0xD5, 0x8A, 0x97, 0xF4, 0x34, 0xDF, 0x83, 0x64, 0x6B, 0x33, 0xCF, 0xBA, 0xB9, 0x0A, 0x62, 0x50, 0x85, 0x1C, 0xF5, 0x3D, 0x4B, 0xDB, + 0x45, 0x26, 0x33, 0x7D, 0xCC, 0xB9, 0xD9, 0x8A, 0x92, 0x16, 0x76, 0xB5, 0x13, 0x65, 0xDD, 0x08, 0xA5, 0x30, 0x4D, 0x2A, 0x93, 0x53, 0x4C, 0x52, 0x42, 0x7E, 0x9A, 0xE5, 0xC1, 0x44, 0x05, 0x92, + 0xC5, 0x53, 0x6E, 0x17, 0x1C, 0xF4, 0xFD, 0x1F, 0x43, 0x57, 0x8F, 0xEA, 0xFB, 0x32, 0xFF, 0x01, 0xD4, 0xFE, 0xD6, 0x35, 0xD7, 0x52, 0x56, 0x8F, 0x90, 0xEC, 0xFB, 0xB1, 0x64, 0xA5, 0xB1, 0x76, + 0x3F, 0x70, 0xC7, 0x2F, 0xD5, 0xBC, 0xDF, 0x61, 0xD0, 0x1F, 0xF3, 0x23, 0x66, 0x39, 0xC9, 0x1C, 0x06, 0x3C, 0x0B, 0x7A, 0x56, 0xAD, 0x03, 0xF4, 0x02, 0x0E, 0x80, 0xBD, 0x9A, 0x5E, 0x2F, 0x16, + 0x1E, 0x05, 0x78, 0x46, 0x9B, 0x99, 0x50, 0x26, 0x6B, 0xA9, 0x6B, 0xBB, 0x73, 0xC0, 0x8E, 0x7F, 0xAE, 0x85, 0x6E, 0x17, 0x03, 0xCF, 0x3C, 0xBD, 0x21, 0x41, 0x80, 0x89, 0x14, 0x8F, 0x7A, 0x9F, + 0x40, 0xD4, 0xD9, 0x11, 0x51, 0xDB, 0xC4, 0xBA, 0xE8, 0x54, 0x23, 0x59, 0xE8, 0x82, 0xA1, 0x9A, 0x99, 0x49, 0xCE, 0xD5, 0xB7, 0x5F, 0xF7, 0xB1, 0x92, 0xDC, 0x27, 0x9B, 0x3E, 0xD1, 0x00, 0x76, + 0x05, 0x3F, 0x58, 0xDE, 0x43, 0x5F, 0xC5, 0x87, 0x56, 0x54, 0xE9, 0x86, 0x33, 0xA3, 0x97, 0x14, 0x11, 0x42, 0x22, 0x9D, 0x8C, 0xD6, 0x13, 0xC6, 0x63, 0x44, 0x32, 0x6D, 0x83, 0x99, 0x2B, 0x3C, + 0x08, 0xF1, 0x7B, 0xE0, 0xEC, 0x28, 0xFB, 0xDB, 0xAB, 0xA1, 0x2C, 0xB0, 0x00, 0xB2, 0xA2, 0xB0, 0x4E, 0x24, 0xD0, 0xC4, 0x1B, 0xD6, 0xB5, 0x80, 0xE9, 0x99, 0xB2, 0x57, 0xC0, 0x07, 0x96, 0x5C, + 0x44, 0x75, 0xA9, 0xD5, 0x31, 0x4C, 0xD6, 0xC1, 0xFB, 0x9F, 0xED, 0xD5, 0x16, 0xE6, 0xB3, 0xC0, 0xDD, 0xD4, 0x04, 0xD6, 0x8D, 0x78, 0xFD, 0x4D, 0xE4, 0x09, 0x31, 0xB1, 0xB8, 0x72, 0xD4, 0xD0, + 0x1A, 0x2D, 0x46, 0xC9, 0xB2, 0x93, 0x90, 0x0D, 0x34, 0xEC, 0x91, 0xD3, 0xB6, 0x93, 0xF4, 0xE7, 0x2C, 0x22, 0x8E, 0xD0, 0x29, 0x4F, 0x6D, 0xC9, 0xB7, 0x17, 0x26, 0x0E, 0xBE, 0x75, 0xA4, 0x71, + 0xEA, 0x4D, 0x78, 0x00, 0xA3, 0xE7, 0xB7, 0xB4, 0x76, 0xD6, 0x4D, 0xEA, 0x6F, 0x4D, 0xA7, 0x26, 0xB3, 0x76, 0xF0, 0x78, 0x00, 0xDB, 0x5F, 0x83, 0xC0, 0xA3, 0xDC, 0xC2, 0xC7, 0x02, 0x6A, 0x4C, + 0x37, 0x8E, 0x88, 0x09, 0x94, 0x88, 0x5D, 0x6F, 0x7A, 0x88, 0x19, 0xD9, 0x1A, 0x2D, 0x50, 0xD1, 0x6D, 0x22, 0xBE, 0x59, 0x2B, 0xED, 0x38, 0x33, 0x04, 0x10, 0xE1, 0x4C, 0xDD, 0xD4, 0xCE, 0x0C, + 0x48, 0xD6, 0x2B, 0x77, 0x97, 0xDE, 0x44, 0xC0, 0x7F, 0x26, 0xA7, 0x9E, 0xF3, 0xA5, 0x83, 0x0F, 0x32, 0x1A, 0x35, 0xAC, 0x50, 0x7E, 0x94, 0x3C, 0x6D, 0xE6, 0x3F, 0xE1, 0x36, 0x82, 0x32, 0x25, + 0xD6, 0xFC, 0x73, 0xD8, 0x6D, 0x4C, 0x84, 0x39, 0x90, 0x13, 0xE0, 0x64, 0xE6, 0x68, 0x34, 0x92, 0x90, 0x7C, 0x7B, 0x78, 0xAE, 0xF2, 0xAA, 0xB1, 0x80, 0xDC, 0x33, 0xE5, 0xE6, 0xBD, 0xBD, 0x6D, + 0x49, 0x0E, 0x3A, 0xA8, 0xBE, 0x8E, 0x82, 0xFA, 0x6C, 0xB1, 0x3B, 0xEA, 0x36, 0x0C, 0x51, 0x0F, 0x9B, 0x4B, 0x5B, 0xA6, 0x64, 0x04, 0x27, 0xAD, 0xDD, 0xF3, 0xD6, 0x6D, 0xED, 0x41, 0xD1, 0xE2, + 0xA0, 0x61, 0x31, 0xE9, 0x50, 0x13, 0x68, 0x42, 0x73, 0x2C, 0x27, 0x34, 0x98, 0xD6, 0xA4, 0x7C, 0xED, 0x4E, 0xD1, 0x89, 0xB6, 0xE7, 0x39, 0x36, 0x1F, 0x68, 0xCC, 0xA0, 0xA9, 0x9D, 0x56, 0x02, + 0xB9, 0x76, 0x55, 0xAB, 0x26, 0x82, 0xE8, 0x37, 0xDB, 0xD6, 0x88, 0xC1, 0x73, 0xDD, 0x49, 0x50, 0xDD, 0x4C, 0xD4, 0xD3, 0xA3, 0x38, 0xF3, 0xFC, 0xFF, 0x8C, 0x71, 0x16, 0xEB, 0xC6, 0x30, 0xD0, + 0x5A, 0xFA, 0xB8, 0xDF, 0x7C, 0x75, 0x60, 0xF4, 0xDE, 0x9A, 0xD9, 0x22, 0x16, 0x26, 0x8E, 0xE1, 0x43, 0xA7, 0x22, 0xC0, 0x34, 0x97, 0xCE, 0x17, 0xEF, 0xE9, 0x8F, 0x67, 0x58, 0x0F, 0x0D, 0xDE, + 0xF5, 0x7F, 0x15, 0x25, 0x5E, 0x68, 0x85, 0x6D, 0x39, 0xA4, 0xEB, 0x33, 0x8A, 0x65, 0x33, 0x46, 0xFE, 0xDE, 0x46, 0x66, 0x3A, 0x62, 0x30, 0x7F, 0x65, 0x90, 0xE2, 0xEE, 0x7A, 0xB9, 0x28, 0xAC, + 0x5E, 0x8F, 0xA1, 0x63, 0xAA, 0x74, 0xE4, 0x02, 0x55, 0xD8, 0xD2, 0x41, 0x66, 0x8A, 0x1C, 0x71, 0x7E, 0x3F, 0x28, 0x99, 0x43, 0x50, 0xF4, 0x99, 0x08, 0xA3, 0x2E, 0x6F, 0xEC, 0x62, 0x06, 0xBD, + 0xF7, 0x93, 0x6D, 0xD2, 0xCF, 0x6A, 0x87, 0xB9, 0x99, 0x40, 0x45, 0x55, 0x2A, 0xCC, 0xE6, 0xEA, 0xF1, 0x29, 0x4E, 0x73, 0x27, 0xA1, 0x3E, 0x6E, 0xAC, 0x16, 0x22, 0x1A, 0x67, 0x6F, 0x60, 0x5D, + 0x6D, 0xA6, 0x36, 0x5D, 0x0D, 0xB0, 0x11, 0x35, 0x40, 0x50, 0x13, 0xF8, 0x74, 0x48, 0x1A, 0x68, 0x33, 0x04, 0x55, 0x28, 0x1A, 0x41, 0xE8, 0x3D, 0xF7, 0x6D, 0x20, 0xD1, 0xDF, 0x75, 0xDF, 0xEC, + 0xA0, 0x91, 0x7F, 0x3E, 0x94, 0xBE, 0xD2, 0x2D, 0x1E, 0xCE, 0xD8, 0xA9, 0xFC, 0x7B, 0x2A, 0x2E, 0x4A, 0x5B, 0x74, 0xD0, 0xB0, 0xC9, 0x28, 0x2B, 0xD6, 0x12, 0xA4, 0x86, 0x48, 0x99, 0x3F, 0x9F, + 0x01, 0x2B, 0xD7, 0x0A, 0x0E, 0x43, 0xDC, 0x3D, 0x1C, 0x0A, 0x16, 0x71, 0x1E, 0xBF, 0x6E, 0xA4, 0x79, 0xDB, 0x94, 0x1F, 0x68, 0xA6, 0x70, 0x1B, 0x57, 0xF7, 0xB8, 0x37, 0xB3, 0x0C, 0x0A, 0x6D, + 0x77, 0x11, 0x23, 0xD6, 0xFC, 0x70, 0xBD, 0xBE, 0x24, 0x44, 0x0C, 0xE4, 0xE2, 0x54, 0xA0, 0x70, 0x53, 0x4F, 0x1C, 0x18, 0x13, 0xC5, 0x16, 0x79, 0x12, 0x60, 0xA7, 0x36, 0x89, 0xDF, 0xE1, 0xBE, + 0xAD, 0x6E, 0xBF, 0x6A, 0xFF, 0x7E, 0xE4, 0x8D, 0xE1, 0xD5, 0x9C, 0x62, 0x22, 0x8B, 0x38, 0x3E, 0x0A, 0xCA, 0x06, 0x90, 0xF8, 0x05, 0xFE, 0xFD, 0xC5, 0x4F, 0xC4, 0xF9, 0x74, 0xBF, 0xAC, 0xCD, + 0xFE, 0x33, 0x21, 0x6C, 0xD2, 0xBC, 0x06, 0xBA, 0x7C, 0x2F, 0x55, 0xD7, 0xA0, 0x70, 0x8C, 0x48, 0x01, 0x4F, 0xF0, 0xC5, 0x35, 0xCD, 0x83, 0xD5, 0x47, 0x08, 0xFD, 0x70, 0x3E, 0x8E, 0xF5, 0x10, + 0xFA, 0x60, 0x72, 0xE2, 0x5F, 0xDA, 0xEB, 0x95, 0x33, 0xD4, 0x80, 0x60, 0x53, 0x07, 0x6C, 0xB8, 0xE4, 0xFE, 0x69, 0x46, 0xFD, 0x1A, 0x67, 0x0D, 0x1B, 0xDA, 0x92, 0x31, 0x1D, 0x5E, 0xD5, 0xFA, + 0x24, 0x5F, 0xA7, 0x4A, 0x6F, 0x04, 0xAE, 0x66, 0xE3, 0xC9, 0xE0, 0xA7, 0x18, 0x2C, 0xFD, 0xB2, 0x10, 0xE5, 0xA2, 0xF2, 0x8C, 0x95, 0x43, 0x99, 0x64, 0x74, 0x2A, 0x98, 0x7A, 0x16, 0x29, 0x85, + 0xDB, 0x91, 0xDF, 0x91, 0xD9, 0x52, 0x9D, 0x8B, 0x85, 0x0B, 0x86, 0x28, 0xA9, 0xC5, 0xC8, 0x45, 0x5B, 0xDB, 0x41, 0x7C, 0x92, 0x72, 0x24, 0xA9, 0xA8, 0xFF, 0xCD, 0xFE, 0x00, 0xC2, 0x28, 0xFA, + 0x28, 0x4C, 0x50, 0x52, 0x57, 0x70, 0x98, 0x15, 0x1E, 0x33, 0x78, 0x7F, 0x82, 0x87, 0xCB, 0x0D, 0x24, 0x31, 0x32, 0x45, 0x55, 0x84, 0x8A, 0x8D, 0x9C, 0xDF, 0xE3, 0xE4, 0xF0, 0xF1, 0x42, 0x61, + 0xD0, 0xFB, 0xFC, 0x02, 0x3C, 0x59, 0x6C, 0x74, 0x9E, 0xAE, 0xFB, 0x0A, 0x17, 0x84, 0xC8, 0xCF, 0xE5, 0xE7, 0x44, 0x8A, 0x98, 0x9F, 0xD8, 0xD9, 0x43, 0x66, 0xB4, 0xC7, 0xD6, 0xFF, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x0F, 0x1E, 0x23, 0x2B, 0x32, 0x38, 0x3E, + }, + }, + { + .name = "Dilithium Round 3, Level 5 (8-7) KAT 1", + .version = 0, + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_87, + .rho_len = 32, + .rho = { + 0xB5, 0x41, 0xC1, 0xE9, 0x2C, 0xEA, 0xDD, 0x90, 0x4A, 0x09, 0xEC, 0x08, 0xAD, 0x30, 0x6D, 0x97, 0x47, 0x34, 0xA0, 0x77, 0x86, 0x84, 0x71, 0xE5, 0x8D, 0x07, 0x71, 0x87, 0xC4, 0x66, 0x04, 0xCF, + }, + .seed_len = 32, + .seed = { + 0x95, 0x2D, 0x21, 0x81, 0xAC, 0x1F, 0x62, 0x59, 0x6F, 0x76, 0x7E, 0xFC, 0xA0, 0xB5, 0x5D, 0xB0, 0x92, 0xEF, 0x81, 0xDB, 0x66, 0xF9, 0xFF, 0xF1, 0x5F, 0x13, 0xD7, 0xAE, 0xEA, 0xCD, 0x8B, 0x3A, + }, + .tr_len = 32, + .tr = { + 0x6C, 0xA7, 0x8E, 0x25, 0x84, 0x0D, 0x7D, 0xA0, 0x3C, 0x92, 0xE0, 0x1B, 0x8D, 0xD2, 0xC6, 0xDB, 0x77, 0xFC, 0x68, 0x70, 0x64, 0x73, 0x6C, 0xA8, 0x44, 0x8D, 0x40, 0x3E, 0x6F, 0x18, 0xC0, 0x2C, + }, + .s1_len = 672, + .s1 = { + 0x03, 0x40, 0x28, 0x8C, 0x88, 0x60, 0x21, 0xB1, 0x90, 0x0C, 0x12, 0x0D, 0x58, 0x18, 0x09, 0x23, 0x44, 0x86, 0x03, 0x02, 0x84, 0x89, 0xB2, 0x28, 0x0C, 0x97, 0x2C, 0x11, 0xC2, 0x09, 0x18, 0x32, + 0x08, 0x09, 0x10, 0x91, 0x14, 0x82, 0x8C, 0x13, 0x03, 0x05, 0x11, 0x01, 0x4C, 0x62, 0x18, 0x8A, 0xDB, 0x08, 0x8A, 0x93, 0x38, 0x12, 0x09, 0xA9, 0x20, 0xE4, 0xA8, 0x41, 0x1A, 0xA1, 0x40, 0xD1, + 0x42, 0x2E, 0x59, 0x92, 0x24, 0xD0, 0x26, 0x00, 0x19, 0x93, 0x84, 0xE2, 0x28, 0x92, 0x1B, 0x19, 0x50, 0xA3, 0x10, 0x8E, 0xA2, 0x28, 0x20, 0x93, 0x34, 0x70, 0x94, 0xC0, 0x4D, 0x24, 0x35, 0x41, + 0x14, 0x05, 0x62, 0xC2, 0x22, 0x31, 0x1A, 0x38, 0x4E, 0xCC, 0x42, 0x44, 0x13, 0x20, 0x82, 0x08, 0x18, 0x6D, 0xE0, 0x14, 0x0D, 0x01, 0x36, 0x61, 0x08, 0x22, 0x29, 0x14, 0xB5, 0x11, 0x49, 0x22, + 0x32, 0xE2, 0x42, 0x26, 0xE4, 0x04, 0x01, 0x5B, 0x48, 0x2A, 0x11, 0x02, 0x60, 0x63, 0x02, 0x48, 0x4A, 0x24, 0x2C, 0x62, 0x40, 0x90, 0x03, 0x41, 0x8D, 0x18, 0xC8, 0x30, 0x82, 0x02, 0x82, 0x51, + 0x98, 0x69, 0xA2, 0x24, 0x50, 0x0A, 0x39, 0x4D, 0x84, 0x00, 0x8E, 0x84, 0x08, 0x21, 0xD9, 0x30, 0x6C, 0xE3, 0x18, 0x29, 0x23, 0x45, 0x6E, 0xCA, 0x24, 0x66, 0x08, 0x21, 0x49, 0x14, 0x16, 0x52, + 0xDA, 0xA0, 0x0C, 0x22, 0x19, 0x62, 0xC1, 0xB8, 0x08, 0x8A, 0x88, 0x8C, 0x22, 0xB1, 0x0C, 0x23, 0xB8, 0x0D, 0x00, 0x93, 0x64, 0x93, 0x16, 0x82, 0x63, 0x32, 0x30, 0xDC, 0xA2, 0x41, 0xD1, 0x48, + 0x42, 0x82, 0xA2, 0x64, 0xD4, 0x24, 0x48, 0x94, 0x48, 0x25, 0x02, 0x82, 0x65, 0xD9, 0x08, 0x69, 0x12, 0x44, 0x21, 0x54, 0x24, 0x70, 0x04, 0x80, 0x84, 0xDA, 0x44, 0x25, 0xA0, 0x24, 0x8A, 0x13, + 0x35, 0x60, 0x84, 0xA0, 0x4C, 0x93, 0x90, 0x48, 0x13, 0x47, 0x02, 0x83, 0x20, 0x05, 0x64, 0xB4, 0x0C, 0x5C, 0x12, 0x72, 0x42, 0x14, 0x86, 0x60, 0x02, 0x12, 0x50, 0x44, 0x04, 0x0B, 0x82, 0x11, + 0x91, 0x18, 0x72, 0x48, 0x88, 0x10, 0xD0, 0x40, 0x4D, 0xCB, 0x98, 0x51, 0x49, 0xA4, 0x8D, 0x18, 0x25, 0x89, 0xD4, 0x32, 0x8E, 0x52, 0xA4, 0x10, 0x11, 0x40, 0x12, 0x88, 0x26, 0x88, 0x21, 0x17, + 0x6A, 0xA2, 0xB2, 0x41, 0xE4, 0x02, 0x89, 0xA1, 0xA0, 0x30, 0x94, 0xC8, 0x41, 0x1B, 0x83, 0x64, 0x12, 0x05, 0x0A, 0x1C, 0x43, 0x8C, 0x84, 0x06, 0x31, 0x0A, 0xA2, 0x6D, 0x24, 0x17, 0x31, 0xC3, + 0x98, 0x28, 0x42, 0x88, 0x25, 0x8C, 0x30, 0x52, 0xA0, 0x02, 0x0E, 0x98, 0x36, 0x88, 0x03, 0x81, 0x31, 0x64, 0x18, 0x6C, 0x09, 0x82, 0x69, 0x19, 0x41, 0x4C, 0xA0, 0x26, 0x11, 0x23, 0x35, 0x60, + 0x01, 0x04, 0x85, 0x64, 0x86, 0x30, 0xD9, 0x20, 0x84, 0xD9, 0x08, 0x2A, 0xDC, 0x32, 0x61, 0x1C, 0xC2, 0x80, 0x89, 0x82, 0x51, 0x14, 0x10, 0x40, 0x19, 0x05, 0x80, 0x58, 0x04, 0x06, 0x99, 0x08, + 0x84, 0x09, 0x27, 0x41, 0xCA, 0x20, 0x8A, 0x93, 0x00, 0x91, 0x03, 0xC6, 0x81, 0xC2, 0xC8, 0x09, 0xC3, 0x30, 0x4D, 0x23, 0x12, 0x0A, 0x9B, 0x42, 0x8D, 0x20, 0x23, 0x6A, 0x54, 0x30, 0x22, 0xCC, + 0xA4, 0x29, 0xA2, 0x18, 0x31, 0x40, 0x20, 0x6E, 0x92, 0x90, 0x48, 0x41, 0xB8, 0x45, 0x83, 0x38, 0x08, 0x5C, 0x46, 0x80, 0x59, 0x36, 0x45, 0xE3, 0xB0, 0x31, 0x18, 0x06, 0x6A, 0x53, 0x16, 0x6D, + 0x21, 0x99, 0x81, 0x00, 0x30, 0x4E, 0xC8, 0x26, 0x48, 0x18, 0xC0, 0x88, 0x19, 0x14, 0x92, 0xC1, 0x98, 0x45, 0x98, 0x08, 0x84, 0x9B, 0x10, 0x4D, 0x0C, 0x96, 0x90, 0x08, 0x91, 0x69, 0x0C, 0xB1, + 0x4D, 0x91, 0x28, 0x6E, 0xC9, 0x06, 0x8C, 0x58, 0x00, 0x0A, 0x0C, 0x96, 0x05, 0x8A, 0x46, 0x06, 0xD4, 0x98, 0x29, 0x83, 0x26, 0x50, 0xE1, 0x10, 0x61, 0xD0, 0x96, 0x50, 0x23, 0x12, 0x24, 0x52, + 0x20, 0x80, 0xE4, 0x04, 0x48, 0x0C, 0x23, 0x92, 0x0B, 0xB7, 0x0D, 0x0C, 0x82, 0x90, 0xD1, 0x10, 0x90, 0x21, 0x22, 0x11, 0x0A, 0x12, 0x64, 0x53, 0xB6, 0x71, 0x99, 0x28, 0x69, 0xC1, 0xC4, 0x4D, + 0x04, 0xA0, 0x8D, 0xCB, 0x96, 0x41, 0x58, 0x14, 0x06, 0x0C, 0x21, 0x70, 0x8B, 0x30, 0x25, 0x52, 0xA2, 0x25, 0x21, 0x19, 0x30, 0x00, 0xA3, 0x28, 0xD0, 0xB8, 0x09, 0xCC, 0x16, 0x12, 0xDC, 0x94, + 0x6D, 0x01, 0x20, 0x81, 0xDC, 0x42, 0x42, 0xE1, 0x28, 0x01, 0x0C, 0x87, 0x89, 0x02, 0x84, 0x09, 0x02, 0x17, 0x88, 0xD8, 0x34, 0x30, 0x1C, 0x33, 0x64, 0x44, 0xA0, 0x09, 0xA0, 0xA0, 0x0D, 0xE3, + 0x90, 0x4D, 0x01, 0x08, 0x65, 0xE2, 0x42, 0x69, 0xA2, 0xC0, 0x91, 0x99, 0x16, 0x62, 0x9B, 0x02, 0x60, 0x40, 0x88, 0x50, 0x40, 0x86, 0x71, 0xA4, 0xC4, 0x61, 0x62, 0x22, 0x20, 0x10, 0x12, 0x11, + }, + .s2_len = 768, + .s2 = { + 0x4B, 0x26, 0x22, 0x09, 0x07, 0x88, 0x1A, 0x26, 0x85, 0x58, 0x86, 0x80, 0xDA, 0xA0, 0x8C, 0x0B, 0x85, 0x68, 0x42, 0x22, 0x82, 0x88, 0x24, 0x61, 0x8C, 0x98, 0x8C, 0x23, 0x30, 0x25, 0x24, 0x40, + 0x45, 0x08, 0xC8, 0x6C, 0x23, 0x14, 0x28, 0x4A, 0x28, 0x10, 0x81, 0x20, 0x72, 0x88, 0x32, 0x26, 0x93, 0xA6, 0x6D, 0x5B, 0xB6, 0x29, 0xC1, 0x24, 0x0D, 0x49, 0x20, 0x70, 0x59, 0x48, 0x26, 0x20, + 0x26, 0x65, 0xCB, 0xA4, 0x88, 0x4A, 0xA6, 0x30, 0x08, 0x45, 0x8E, 0x00, 0x32, 0x88, 0x24, 0x33, 0x0D, 0xA1, 0x46, 0x72, 0x9B, 0x12, 0x00, 0x14, 0xB5, 0x21, 0xE3, 0x02, 0x09, 0x23, 0x42, 0x28, + 0x19, 0xB2, 0x05, 0x92, 0xA4, 0x44, 0x00, 0x06, 0x45, 0x04, 0xC6, 0x29, 0x5C, 0x12, 0x50, 0xA2, 0x90, 0x45, 0x92, 0x22, 0x86, 0x9B, 0x24, 0x31, 0x9C, 0x12, 0x65, 0x94, 0xB0, 0x01, 0x98, 0x26, + 0x65, 0xD2, 0x48, 0x0E, 0x62, 0x46, 0x20, 0x89, 0x82, 0x61, 0x08, 0x45, 0x08, 0x64, 0xA6, 0x91, 0x9C, 0x42, 0x6D, 0x9A, 0x96, 0x0C, 0x49, 0x24, 0x32, 0x04, 0xB1, 0x65, 0x83, 0x16, 0x45, 0x8A, + 0x22, 0x22, 0x1A, 0x42, 0x02, 0x83, 0x46, 0x2C, 0x1C, 0x33, 0x72, 0x5A, 0x24, 0x00, 0xD4, 0x30, 0x80, 0x0A, 0x23, 0x08, 0x24, 0xA4, 0x84, 0x01, 0xC0, 0x41, 0x44, 0xC0, 0x09, 0x51, 0xA8, 0x2C, + 0x01, 0x20, 0x8D, 0x82, 0x14, 0x72, 0x23, 0x30, 0x12, 0x11, 0x12, 0x52, 0x0A, 0x11, 0x00, 0x00, 0x43, 0x90, 0xDC, 0x36, 0x4D, 0x88, 0x96, 0x05, 0xC9, 0xB8, 0x45, 0x64, 0x02, 0x4A, 0x61, 0x00, + 0x0C, 0x82, 0x18, 0x4E, 0x91, 0x00, 0x8E, 0x23, 0x12, 0x91, 0x41, 0xB8, 0x91, 0x1B, 0x18, 0x0C, 0x0B, 0x46, 0x89, 0xD2, 0x18, 0x8D, 0x19, 0x84, 0x10, 0xC0, 0x86, 0x0D, 0x03, 0x16, 0x25, 0xC3, + 0xC2, 0x70, 0x19, 0x87, 0x31, 0x1A, 0x24, 0x2C, 0x08, 0x14, 0x01, 0x14, 0x04, 0x6C, 0xC2, 0x46, 0x04, 0x13, 0x10, 0x06, 0xC9, 0x08, 0x49, 0x04, 0xB1, 0x70, 0x54, 0xA2, 0x0C, 0x01, 0x24, 0x6A, + 0x90, 0x18, 0x45, 0x24, 0x47, 0x49, 0x1B, 0xA2, 0x40, 0x02, 0x32, 0x80, 0x60, 0x98, 0x50, 0x8B, 0x48, 0x91, 0x5A, 0x46, 0x12, 0x13, 0x49, 0x71, 0x1C, 0x96, 0x01, 0x22, 0x15, 0x29, 0x20, 0xB5, + 0x00, 0x04, 0xC3, 0x05, 0x4C, 0x24, 0x12, 0x80, 0x40, 0x4E, 0x14, 0xA1, 0x4C, 0xDB, 0x16, 0x4D, 0x00, 0x08, 0x24, 0xE2, 0x48, 0x80, 0xD4, 0x98, 0x44, 0x89, 0xC2, 0x68, 0x84, 0x24, 0x52, 0x02, + 0x24, 0x61, 0x5C, 0x38, 0x11, 0x60, 0x96, 0x44, 0xA3, 0x02, 0x0E, 0x04, 0xB5, 0x81, 0xD1, 0x48, 0x24, 0xE0, 0x18, 0x49, 0x91, 0x06, 0x88, 0x93, 0x88, 0x61, 0x52, 0xA8, 0x20, 0x50, 0x22, 0x85, + 0x23, 0x28, 0x2C, 0xC3, 0x08, 0x12, 0x89, 0x22, 0x8D, 0x11, 0x22, 0x0D, 0xC2, 0x30, 0x12, 0x0A, 0x98, 0x2D, 0x22, 0x19, 0x86, 0x08, 0x89, 0x40, 0x0B, 0x21, 0x69, 0x04, 0xB3, 0x00, 0x61, 0x38, + 0x0D, 0x04, 0x10, 0x2D, 0x5A, 0x24, 0x65, 0x8C, 0x12, 0x0A, 0x5C, 0x42, 0x0E, 0x5A, 0x26, 0x90, 0xA1, 0x36, 0x88, 0xA1, 0x38, 0x4D, 0x1B, 0x04, 0x8E, 0xDC, 0x00, 0x0A, 0x0B, 0x35, 0x6A, 0xC2, + 0x02, 0x91, 0x83, 0x48, 0x20, 0x11, 0x02, 0x86, 0xD2, 0xA2, 0x2D, 0x1C, 0x00, 0x29, 0x0C, 0x30, 0x12, 0x20, 0x91, 0x6D, 0x02, 0x87, 0x91, 0x40, 0x82, 0x44, 0x09, 0x98, 0x4C, 0x24, 0x13, 0x52, + 0x09, 0x92, 0x4C, 0x4A, 0xB0, 0x01, 0x01, 0x46, 0x80, 0x10, 0x03, 0x44, 0x94, 0xB6, 0x49, 0xDC, 0xA0, 0x51, 0xA4, 0x04, 0x0C, 0x14, 0xC6, 0x68, 0x24, 0x09, 0x22, 0x9B, 0x20, 0x0E, 0x09, 0x28, + 0x69, 0xDA, 0x16, 0x69, 0x09, 0xA4, 0x80, 0x0C, 0x39, 0x60, 0xDC, 0xC0, 0x10, 0x23, 0x89, 0x0D, 0xDB, 0x10, 0x41, 0xCB, 0xB2, 0x6C, 0x12, 0xC2, 0x04, 0x08, 0x92, 0x68, 0xCA, 0x06, 0x20, 0xE0, + 0x36, 0x0E, 0x04, 0xC2, 0x49, 0x18, 0x27, 0x68, 0x24, 0xA8, 0x29, 0x42, 0x42, 0x6A, 0x8B, 0xB6, 0x25, 0x82, 0x26, 0x00, 0x1C, 0x07, 0x42, 0x1B, 0x02, 0x26, 0x94, 0x90, 0x85, 0x13, 0xA7, 0x30, + 0x09, 0x24, 0x40, 0x5A, 0xA8, 0x44, 0x49, 0x00, 0x8A, 0x59, 0x18, 0x24, 0x90, 0x28, 0x80, 0x88, 0x08, 0x71, 0x21, 0x47, 0x2D, 0x52, 0x34, 0x80, 0x0B, 0x96, 0x04, 0x9C, 0x38, 0x09, 0x8C, 0xA4, + 0x30, 0x19, 0xA9, 0x8C, 0x03, 0x45, 0x4C, 0x51, 0xA0, 0x68, 0x04, 0x22, 0x42, 0x11, 0x18, 0x82, 0xA2, 0x96, 0x48, 0xE4, 0x36, 0x72, 0xCB, 0x24, 0x28, 0x23, 0xA7, 0x2D, 0xDC, 0x38, 0x00, 0x89, + 0x36, 0x06, 0x4B, 0x92, 0x89, 0x03, 0x49, 0x71, 0xDA, 0x10, 0x06, 0x0A, 0x39, 0x0C, 0x40, 0x14, 0x82, 0xDA, 0x80, 0x48, 0x9A, 0x86, 0x88, 0x59, 0x44, 0x50, 0x89, 0xC4, 0x61, 0x59, 0x22, 0x42, + 0x10, 0xB0, 0x24, 0x8B, 0x40, 0x6C, 0x8C, 0x20, 0x46, 0x23, 0x09, 0x60, 0xC4, 0x98, 0x85, 0x5A, 0xA4, 0x01, 0x01, 0x39, 0x46, 0xC1, 0x94, 0x71, 0x8C, 0xC2, 0x40, 0x0C, 0x22, 0x25, 0x53, 0x00, + 0x66, 0x4C, 0x26, 0x30, 0x21, 0xC0, 0x2D, 0x98, 0x30, 0x6A, 0x94, 0x24, 0x50, 0x21, 0x12, 0x81, 0x0B, 0x12, 0x00, 0x9C, 0x94, 0x0C, 0x9B, 0x36, 0x6C, 0x94, 0x26, 0x85, 0x8A, 0x12, 0x30, 0xA3, + 0xA0, 0x89, 0x42, 0x08, 0x50, 0x44, 0x16, 0x2C, 0x20, 0x38, 0x29, 0x5C, 0x32, 0x61, 0x63, 0xA4, 0x6D, 0x58, 0x48, 0x72, 0xDA, 0x26, 0x22, 0x89, 0xA4, 0x8D, 0xD3, 0x32, 0x26, 0x0C, 0x32, 0x04, + }, + .t0_len = 3328, + .t0 = { + 0xDD, 0x9E, 0x51, 0x56, 0xEB, 0x0F, 0xB3, 0x78, 0x1A, 0x12, 0x27, 0x3B, 0xE3, 0x14, 0xE7, 0x1E, 0x56, 0x59, 0x60, 0x44, 0xDA, 0x83, 0xAB, 0xFB, 0x24, 0xC7, 0x79, 0x9A, 0x81, 0x46, 0x43, 0x4E, + 0x93, 0x49, 0x03, 0x49, 0x29, 0x00, 0x0A, 0xF0, 0x29, 0xBA, 0x14, 0x68, 0x07, 0x48, 0xA8, 0x99, 0xE8, 0x3D, 0xD9, 0x21, 0x1D, 0x3E, 0x8D, 0xE8, 0x41, 0x9C, 0xE1, 0x20, 0xCF, 0x5B, 0xCA, 0x55, + 0x29, 0x7A, 0x27, 0xD8, 0x35, 0x4F, 0x66, 0xFB, 0x83, 0x7B, 0x10, 0x8D, 0x7D, 0xC7, 0xE3, 0x2D, 0x14, 0x5B, 0xB4, 0x01, 0x65, 0x24, 0x42, 0xEB, 0xF5, 0x45, 0xC4, 0xA1, 0x2C, 0x70, 0x19, 0x18, + 0xD2, 0x49, 0x4C, 0x03, 0xA1, 0x12, 0xC0, 0xD9, 0x42, 0xDC, 0xB4, 0x4D, 0xFA, 0xEC, 0x31, 0xAE, 0xAA, 0xE3, 0x2A, 0x5B, 0xAD, 0xBB, 0x8C, 0x82, 0xC6, 0x21, 0x77, 0x1C, 0xEA, 0x9A, 0x1E, 0xDA, + 0xF7, 0x7B, 0x77, 0x7C, 0x52, 0x40, 0x28, 0x67, 0x04, 0xC0, 0x61, 0xC3, 0xAA, 0x6D, 0x68, 0x51, 0x22, 0xB4, 0xC9, 0x82, 0x46, 0x7C, 0x32, 0x9C, 0xDF, 0x89, 0x9D, 0x00, 0xF3, 0x01, 0xC5, 0x54, + 0xAF, 0x57, 0xE2, 0xF9, 0x93, 0x4C, 0x3A, 0x3F, 0x36, 0xEE, 0x2D, 0xD5, 0xCB, 0x35, 0x6C, 0x47, 0x52, 0x08, 0x30, 0x79, 0x81, 0x78, 0x00, 0xA0, 0x92, 0x84, 0x51, 0x27, 0x8A, 0x26, 0xCC, 0xD6, + 0x07, 0x17, 0xD4, 0x17, 0x59, 0xBC, 0x8C, 0x6F, 0x77, 0x9A, 0xFA, 0xBD, 0xFD, 0xFA, 0xFA, 0xA3, 0xA4, 0xD6, 0x2E, 0x9D, 0x1E, 0x9B, 0x3C, 0x8E, 0xDB, 0xAF, 0xBE, 0x29, 0xD7, 0x8E, 0x4D, 0x71, + 0xB0, 0xCE, 0x4C, 0xF4, 0xCF, 0x15, 0x1E, 0x3E, 0x54, 0x1C, 0x29, 0x9C, 0x6E, 0xAD, 0x63, 0xA7, 0x27, 0x15, 0xCD, 0xC9, 0x5F, 0x58, 0x4C, 0x6E, 0xB3, 0x75, 0x7C, 0x66, 0x0A, 0x27, 0x59, 0x63, + 0x19, 0x2B, 0xA8, 0xFD, 0xE8, 0xC2, 0xAC, 0xBD, 0x7E, 0xA9, 0xE5, 0x25, 0x92, 0x62, 0x42, 0x66, 0x59, 0xF7, 0xA5, 0x55, 0x5B, 0x80, 0xBD, 0x2C, 0xD5, 0xE7, 0xB5, 0xA6, 0xC9, 0x9B, 0x03, 0x0C, + 0x88, 0x70, 0x90, 0xEE, 0x9E, 0x64, 0x67, 0xA3, 0x75, 0x5A, 0x07, 0x58, 0xC9, 0xFF, 0xD7, 0xDB, 0x4D, 0x9D, 0x03, 0x1B, 0x7B, 0x6C, 0x77, 0xCC, 0x5D, 0xA2, 0x8A, 0xF2, 0xA6, 0xD3, 0x3A, 0x25, + 0x18, 0x7F, 0x7E, 0x2F, 0x5E, 0x45, 0xDD, 0x48, 0xE5, 0x1B, 0xBE, 0xAA, 0x9C, 0x06, 0xE5, 0xD2, 0xE8, 0xB0, 0x0D, 0x92, 0x58, 0x32, 0x31, 0xBB, 0xE0, 0x1F, 0x2A, 0x78, 0xA9, 0xFE, 0xB5, 0x10, + 0x72, 0xC2, 0xF1, 0x13, 0x8A, 0x5C, 0x68, 0x15, 0x78, 0x66, 0x6F, 0xE5, 0x46, 0x85, 0x00, 0xB6, 0x16, 0xAC, 0x60, 0x40, 0x22, 0x5F, 0xF0, 0xA8, 0xE9, 0xBF, 0x86, 0xD6, 0x45, 0x0F, 0xD2, 0xAC, + 0x8C, 0x2A, 0x3F, 0x0A, 0xE0, 0x67, 0x93, 0xBD, 0xE4, 0x34, 0x71, 0x4F, 0x1F, 0xCA, 0x30, 0xC7, 0xB1, 0x41, 0x34, 0xFF, 0xB5, 0xE7, 0x43, 0x72, 0x52, 0x17, 0x0C, 0xD4, 0x2E, 0x04, 0xBB, 0x76, + 0xF5, 0x36, 0x5A, 0x3C, 0x2F, 0x80, 0xF0, 0x2A, 0x86, 0xC4, 0x07, 0xB9, 0x84, 0x03, 0xBA, 0x84, 0x8C, 0xCD, 0xF5, 0x4B, 0x60, 0x09, 0x21, 0x77, 0x46, 0x85, 0x0A, 0x67, 0x03, 0x84, 0x4A, 0x49, + 0x6E, 0x1A, 0x09, 0x21, 0x9D, 0xA8, 0xA6, 0x40, 0xC9, 0x20, 0x67, 0xC0, 0xBB, 0x66, 0xA5, 0x70, 0x00, 0x78, 0x50, 0xF9, 0xB3, 0x03, 0x33, 0xA6, 0x68, 0x28, 0x3D, 0x5A, 0x15, 0xB0, 0xAF, 0x09, + 0x9D, 0xEA, 0x4F, 0x52, 0xDF, 0x86, 0x5B, 0xC3, 0x58, 0x6A, 0x8C, 0x04, 0x73, 0xE7, 0xDA, 0x12, 0xDA, 0xA1, 0xA5, 0x0B, 0xF7, 0xCA, 0x5E, 0x2B, 0xBD, 0x53, 0xCB, 0xAD, 0xDC, 0xBA, 0x09, 0x18, + 0x29, 0x44, 0xE8, 0x1B, 0xAE, 0xC6, 0x0D, 0xAE, 0xD7, 0x8A, 0xA8, 0xB6, 0xC3, 0xA2, 0xF4, 0x5B, 0x07, 0x16, 0xAA, 0x84, 0x29, 0xA1, 0x06, 0xDD, 0x71, 0x69, 0x40, 0x29, 0xFD, 0x1A, 0x02, 0xC5, + 0xCA, 0x2D, 0x3D, 0xFD, 0xE3, 0x2E, 0xCD, 0xC5, 0x78, 0x0F, 0x72, 0x3F, 0x1E, 0x2D, 0xB7, 0x68, 0xA5, 0xA3, 0xCD, 0xAE, 0x48, 0xF9, 0x39, 0xCA, 0x15, 0x86, 0xE2, 0x30, 0x83, 0xF7, 0x3C, 0x2F, + 0x62, 0x3A, 0x12, 0x1F, 0x54, 0x67, 0xAF, 0x24, 0xDA, 0xA8, 0x72, 0x63, 0x98, 0xEE, 0xED, 0x8B, 0xB1, 0xDF, 0xA4, 0x60, 0xA1, 0x12, 0xC5, 0x97, 0xAE, 0x2D, 0xD6, 0x4E, 0x90, 0x40, 0x02, 0xE0, + 0xF1, 0xA9, 0x0C, 0x00, 0xF9, 0x2C, 0xAF, 0xFA, 0x7F, 0xC4, 0x46, 0x74, 0x44, 0xA6, 0xFC, 0x40, 0x39, 0x18, 0x80, 0x3A, 0x92, 0xDC, 0x2A, 0xFC, 0x3A, 0x17, 0xBC, 0xAC, 0x18, 0x7A, 0xD8, 0xB3, + 0xDE, 0x0D, 0x87, 0x28, 0x30, 0xB8, 0xA7, 0xB5, 0xE5, 0x58, 0x0A, 0xBD, 0x1E, 0x27, 0xD5, 0x59, 0x4C, 0x1A, 0x6A, 0x00, 0x3D, 0x6C, 0x7C, 0x21, 0xB8, 0x71, 0xC7, 0xB6, 0x31, 0x49, 0x7A, 0x2E, + 0xFE, 0x0F, 0x86, 0x2B, 0x65, 0xF6, 0x65, 0x6B, 0x09, 0x4D, 0xDB, 0xA8, 0x20, 0xE9, 0xE6, 0x31, 0x4B, 0x4B, 0xD8, 0xF7, 0x81, 0x51, 0x8D, 0x17, 0x40, 0x54, 0x97, 0xBB, 0x39, 0x06, 0x3E, 0x68, + 0x33, 0xB0, 0x4D, 0xE0, 0xD3, 0x6B, 0xFC, 0x9F, 0x06, 0x14, 0xDC, 0xB7, 0xDE, 0x8D, 0x31, 0xF0, 0xE0, 0x1A, 0xB1, 0x50, 0xDE, 0x23, 0xC9, 0xD5, 0x2F, 0x80, 0x14, 0xE8, 0x85, 0x7E, 0x78, 0x6D, + 0xCA, 0xED, 0x8E, 0xA4, 0x1F, 0x78, 0x09, 0x97, 0x39, 0x4F, 0x87, 0x7F, 0x52, 0x8B, 0x59, 0x9F, 0xDB, 0x85, 0x7E, 0x8F, 0xCF, 0xCA, 0x77, 0x4F, 0x35, 0x08, 0x46, 0xD0, 0x5F, 0x97, 0x3C, 0x2A, + 0x1C, 0xF5, 0xFF, 0x0C, 0x58, 0xE3, 0x75, 0x90, 0xA6, 0x2F, 0x5B, 0x2A, 0x3B, 0x21, 0x26, 0x20, 0x63, 0x68, 0x2D, 0xBB, 0x0A, 0x20, 0x50, 0xBA, 0xD8, 0x44, 0x99, 0xEF, 0x5C, 0xAD, 0xCF, 0xFE, + 0x41, 0xB0, 0xE7, 0x1B, 0x3F, 0x4F, 0xC3, 0x5E, 0x1E, 0x37, 0x60, 0x48, 0xE3, 0xA3, 0x4B, 0xF6, 0xBC, 0xF4, 0xF6, 0x1D, 0x2D, 0x3C, 0x35, 0x39, 0x54, 0x24, 0x94, 0xFB, 0x04, 0x57, 0xBB, 0x76, + 0x2F, 0x03, 0x99, 0x63, 0x21, 0x35, 0x0B, 0x64, 0x87, 0x4B, 0xBD, 0xCE, 0x72, 0x04, 0xAB, 0x86, 0x06, 0x24, 0x58, 0x34, 0xE5, 0x99, 0x35, 0x2C, 0x36, 0x8D, 0x36, 0xC2, 0xC4, 0x63, 0x49, 0x76, + 0x11, 0x9B, 0xF9, 0x72, 0xC3, 0xA4, 0xAB, 0x28, 0x76, 0x67, 0x7B, 0xEE, 0x0E, 0xBC, 0xBE, 0x30, 0xF1, 0x31, 0x66, 0x2D, 0x68, 0x64, 0x7E, 0xD5, 0xD0, 0xA8, 0xF6, 0xC8, 0x9A, 0xFB, 0xBC, 0x8B, + 0xFA, 0xF1, 0xD1, 0x1B, 0x20, 0x6C, 0x33, 0x17, 0xAE, 0xD7, 0x88, 0x21, 0x35, 0x95, 0x72, 0x70, 0xEF, 0x87, 0x85, 0x2A, 0x32, 0x0A, 0x9B, 0x18, 0x4A, 0x60, 0x8C, 0xA6, 0xBC, 0x82, 0x58, 0x38, + 0x2E, 0x0B, 0x19, 0xBE, 0xAA, 0x38, 0x41, 0x62, 0x3F, 0xA3, 0x07, 0x93, 0xD8, 0xF4, 0x99, 0xB8, 0x37, 0xC4, 0x40, 0xCC, 0x11, 0x3C, 0x70, 0x35, 0x0C, 0x01, 0xC3, 0xE1, 0xAC, 0xE0, 0x53, 0xDB, + 0x30, 0xED, 0xFF, 0x7B, 0xA5, 0x26, 0x9D, 0x41, 0x8E, 0x8E, 0x48, 0xB9, 0x2A, 0xAC, 0x17, 0x09, 0x3D, 0x58, 0xE3, 0xAD, 0xDC, 0x78, 0xDA, 0x7B, 0xCF, 0xD9, 0xA8, 0xA8, 0xCA, 0xAB, 0x3D, 0xA2, + 0x5A, 0x46, 0x34, 0xC1, 0xBC, 0x95, 0xC6, 0x4E, 0xDF, 0x2F, 0x6F, 0xE7, 0xED, 0xFB, 0xAA, 0x1B, 0xAD, 0x2D, 0x23, 0x12, 0x98, 0x0B, 0xD6, 0x80, 0xB0, 0x68, 0x92, 0xB5, 0x55, 0xF3, 0x16, 0x74, + 0xA9, 0x52, 0xA1, 0x25, 0xE8, 0x87, 0x10, 0x4D, 0x1C, 0xF8, 0x3E, 0x97, 0xA0, 0x59, 0x0F, 0x47, 0x2B, 0xB3, 0xD1, 0xA2, 0xB9, 0x08, 0x32, 0x3B, 0x0E, 0xA9, 0x9F, 0x8F, 0x91, 0xFA, 0x30, 0xB9, + 0x09, 0x42, 0xD7, 0xB6, 0x90, 0xAF, 0xC6, 0x1A, 0x02, 0x77, 0x99, 0xD7, 0x70, 0x2D, 0x56, 0xB7, 0x68, 0x6A, 0x8F, 0x9B, 0xB0, 0x4E, 0xDE, 0xE3, 0xCF, 0xA3, 0x92, 0x7E, 0xF5, 0x16, 0xA7, 0xF5, + 0x20, 0x88, 0x59, 0x07, 0x31, 0x9B, 0x95, 0x84, 0xC8, 0x24, 0xFE, 0x97, 0xDC, 0xAF, 0xBA, 0xB5, 0xA3, 0xA7, 0x26, 0x71, 0xBA, 0x0C, 0x21, 0x88, 0x37, 0x91, 0x3B, 0x16, 0x1B, 0x42, 0x70, 0x6B, + 0x9B, 0x85, 0xCB, 0x42, 0x3B, 0x9D, 0xE5, 0xF2, 0x3C, 0x23, 0x80, 0x0B, 0x9C, 0x07, 0x11, 0x13, 0x2C, 0x40, 0x34, 0x75, 0x8D, 0x2E, 0xC8, 0x6D, 0xF5, 0x78, 0xE1, 0xB9, 0xF1, 0x78, 0x5F, 0x5C, + 0x79, 0x5C, 0x8B, 0xC2, 0x0F, 0xBC, 0xFF, 0xD9, 0xE4, 0xCA, 0x2E, 0x93, 0xC7, 0xCA, 0xE4, 0xDA, 0x91, 0xB9, 0xC0, 0x0E, 0x77, 0x8E, 0x3C, 0x42, 0x86, 0x53, 0x0C, 0x6C, 0x80, 0xC1, 0x02, 0x7C, + 0x8F, 0xA0, 0xDD, 0x78, 0xCF, 0x0A, 0x55, 0x4A, 0xD2, 0x7B, 0x19, 0xAF, 0x2B, 0x0C, 0x28, 0xE0, 0x50, 0xD0, 0x35, 0x5F, 0xE6, 0x1D, 0xE7, 0xF7, 0x02, 0xDC, 0x07, 0x3C, 0x90, 0x47, 0xC9, 0x7D, + 0x87, 0xC8, 0x15, 0x78, 0xD1, 0x98, 0xD9, 0x7B, 0x52, 0x3E, 0xBB, 0x15, 0x06, 0xD9, 0xA7, 0x52, 0x92, 0x46, 0x5E, 0x44, 0x0B, 0x20, 0x6F, 0xF9, 0x53, 0xE4, 0xA6, 0x8C, 0xBC, 0x57, 0x3E, 0x7C, + 0x36, 0x45, 0xE2, 0xF8, 0xC0, 0x8F, 0xDA, 0x3B, 0xD5, 0x8E, 0xD1, 0xC9, 0x0A, 0x4F, 0x63, 0xED, 0xFD, 0xF2, 0x0C, 0x8B, 0x25, 0x7E, 0xC9, 0x16, 0xCD, 0x6A, 0xEA, 0xB8, 0xEB, 0xA4, 0x77, 0xC1, + 0xF4, 0xC0, 0x9B, 0x8F, 0x69, 0xD6, 0xFE, 0xD9, 0x33, 0x19, 0xED, 0xA8, 0xEC, 0xF8, 0xC0, 0xEF, 0xE8, 0x4E, 0x5E, 0xC2, 0x71, 0x96, 0x66, 0x8E, 0x00, 0x71, 0xA0, 0x39, 0xDF, 0x3D, 0xBB, 0x87, + 0x2B, 0x88, 0xAC, 0xC8, 0x53, 0xA0, 0x82, 0x20, 0x6B, 0x95, 0xE0, 0x64, 0x34, 0xFC, 0xBF, 0x3F, 0xA3, 0x09, 0xDA, 0xE2, 0x5A, 0x25, 0x1D, 0xDB, 0x58, 0x40, 0x71, 0x81, 0x39, 0xCA, 0xDF, 0x13, + 0xF3, 0x92, 0xE0, 0xCE, 0x7B, 0x9C, 0x27, 0x17, 0x22, 0x26, 0xEE, 0x84, 0x71, 0xD0, 0x13, 0xB1, 0xFF, 0x45, 0x42, 0x97, 0xB7, 0x81, 0xAB, 0xAC, 0xEA, 0x43, 0x2D, 0x41, 0xFC, 0xF6, 0x9D, 0xB8, + 0x85, 0x6E, 0x37, 0x7B, 0x8B, 0x4E, 0x24, 0x00, 0x86, 0xD2, 0xFB, 0x73, 0x11, 0x88, 0x51, 0x45, 0x06, 0x9A, 0x72, 0x09, 0x86, 0x9D, 0xB0, 0x61, 0xA2, 0x45, 0xB9, 0x62, 0xE1, 0x86, 0x81, 0x0A, + 0x19, 0x23, 0x74, 0x70, 0x18, 0x85, 0x79, 0x31, 0x24, 0x69, 0x84, 0x7C, 0x53, 0x85, 0x66, 0x6E, 0xA0, 0xF3, 0xB5, 0x94, 0x22, 0xC0, 0xF6, 0x9B, 0x09, 0xB5, 0xB8, 0xBD, 0x08, 0x07, 0xCE, 0x99, + 0x92, 0x14, 0x2A, 0x34, 0xEE, 0x32, 0x7E, 0x8F, 0xDA, 0x2C, 0xBA, 0x0F, 0x40, 0x10, 0xF6, 0xD5, 0x24, 0xFF, 0x0C, 0x5B, 0xE4, 0x12, 0x9E, 0x98, 0xB2, 0x01, 0xAB, 0x91, 0x8A, 0x52, 0x76, 0xA7, + 0x35, 0x6B, 0x15, 0x2E, 0x60, 0x70, 0xCF, 0xDC, 0x27, 0x0C, 0x5D, 0x8D, 0x70, 0x8E, 0xE8, 0xCB, 0xB7, 0x01, 0x95, 0xCF, 0xA6, 0xA2, 0x9E, 0x8B, 0x07, 0x2F, 0x25, 0xF0, 0x3F, 0x25, 0x36, 0x2D, + 0x59, 0x0F, 0x5B, 0xB2, 0xB6, 0x7B, 0xD6, 0x3F, 0x3F, 0xA5, 0x2F, 0x2C, 0x61, 0x1D, 0x72, 0x57, 0x25, 0xF0, 0x42, 0xD5, 0x82, 0x4C, 0x77, 0x3C, 0xF8, 0xE6, 0x1F, 0xED, 0xBA, 0x92, 0xC5, 0x80, + 0xDC, 0xA7, 0x33, 0x48, 0xEC, 0x67, 0x60, 0x9D, 0x30, 0x1E, 0x74, 0x16, 0x44, 0xAA, 0x3A, 0x0B, 0x24, 0x41, 0xC5, 0x88, 0xED, 0x7F, 0x17, 0x1B, 0xC7, 0xB9, 0x54, 0x92, 0xEF, 0x14, 0xAE, 0xB5, + 0x44, 0x78, 0x6F, 0x23, 0x27, 0x35, 0x08, 0x56, 0x1C, 0xCB, 0x81, 0x03, 0xE2, 0xFA, 0x97, 0xD3, 0x5F, 0x29, 0xD7, 0xDE, 0x89, 0x08, 0x97, 0xF1, 0xEC, 0x97, 0x41, 0x81, 0xC7, 0x9B, 0xE3, 0x20, + 0x01, 0xFC, 0x0E, 0x91, 0xA0, 0xFB, 0xD7, 0xB0, 0xEF, 0xB8, 0xCC, 0x2D, 0xB6, 0x19, 0xD3, 0x64, 0x85, 0xCC, 0xCF, 0xD3, 0xB5, 0xDB, 0x94, 0xC0, 0x82, 0x0A, 0x53, 0x6C, 0xC8, 0xA2, 0xD7, 0x8F, + 0x5A, 0x9B, 0x95, 0xCE, 0xF4, 0xD3, 0x7B, 0xC8, 0x74, 0x14, 0x22, 0xBB, 0x61, 0xC3, 0xD0, 0xFE, 0x5B, 0xA4, 0x9D, 0x75, 0x42, 0x67, 0xA0, 0x10, 0x31, 0xF4, 0xDF, 0x52, 0xDE, 0xFF, 0xB5, 0xC8, + 0x98, 0xA0, 0x96, 0x47, 0xEF, 0x3F, 0x02, 0x4F, 0xCD, 0xD9, 0x0E, 0xFA, 0x94, 0x38, 0xC9, 0xDE, 0x93, 0xAA, 0xD9, 0x8E, 0xFF, 0x29, 0x49, 0xEE, 0xC8, 0xBC, 0x3A, 0x0F, 0x3E, 0x60, 0xE4, 0xB5, + 0x6B, 0xED, 0x02, 0x63, 0xE0, 0x4A, 0x5D, 0x3C, 0x68, 0x68, 0x76, 0x49, 0xA1, 0x00, 0x58, 0x34, 0x88, 0xF9, 0x83, 0xCD, 0x7F, 0x43, 0x41, 0x30, 0x90, 0xFC, 0x88, 0x0C, 0x11, 0xE8, 0x5E, 0xDC, + 0x24, 0x44, 0x6C, 0x35, 0x70, 0xAA, 0xB5, 0xDA, 0xEE, 0x3B, 0x7E, 0xD4, 0xD3, 0x53, 0x98, 0x8D, 0x02, 0xC7, 0x3D, 0x77, 0x7D, 0xCE, 0x26, 0xD1, 0x2A, 0x39, 0x5E, 0xB1, 0xB9, 0x5F, 0xFC, 0x7A, + 0xB5, 0x83, 0x43, 0xAE, 0xCD, 0x2D, 0xCE, 0xCA, 0xB0, 0x0A, 0x97, 0xF5, 0x78, 0xB9, 0x32, 0x7D, 0x0A, 0x9D, 0x1F, 0xDB, 0x65, 0x10, 0xF8, 0x60, 0x68, 0x5C, 0xC3, 0x03, 0x6F, 0xD8, 0x32, 0x6F, + 0x59, 0xA4, 0xE9, 0xA0, 0xDD, 0x7B, 0x02, 0xCE, 0x1D, 0x36, 0xBF, 0x46, 0xF4, 0xFA, 0x41, 0x15, 0x17, 0x2C, 0xBF, 0xDA, 0xDA, 0x6D, 0x59, 0x35, 0x26, 0xB7, 0x47, 0xE2, 0x36, 0x7B, 0x10, 0xA8, + 0x83, 0x92, 0x68, 0x7D, 0xE2, 0x23, 0xBF, 0x1D, 0x5A, 0xF1, 0xD7, 0x3D, 0x8A, 0x24, 0x84, 0x5C, 0x87, 0xFF, 0x76, 0x67, 0x5D, 0x73, 0xD5, 0x09, 0xF2, 0x83, 0xDA, 0x66, 0xB9, 0x43, 0xAD, 0x45, + 0x6A, 0xFE, 0x70, 0x92, 0x51, 0xB1, 0x7F, 0x9E, 0x43, 0x58, 0x7E, 0x52, 0x0C, 0xD6, 0xA1, 0xE9, 0xA2, 0x4B, 0x55, 0x8F, 0x4F, 0x6E, 0x46, 0x57, 0xF4, 0xC6, 0x35, 0x1D, 0xEA, 0x9B, 0xB9, 0x47, + 0xB3, 0x2D, 0xC4, 0x6E, 0x35, 0x20, 0xFC, 0xE3, 0xBD, 0x21, 0x97, 0x3C, 0x3B, 0x8B, 0x95, 0x15, 0x04, 0x58, 0xCB, 0x5E, 0x42, 0x48, 0xE2, 0x6D, 0x6E, 0x52, 0xE7, 0x6B, 0x8E, 0x6B, 0xF2, 0xBC, + 0xE3, 0xC8, 0xAC, 0x1C, 0x6C, 0xFD, 0x7F, 0x43, 0x51, 0x3A, 0x91, 0x8F, 0xEC, 0x31, 0xCE, 0xC0, 0xD4, 0x29, 0x66, 0x05, 0xAB, 0x21, 0xBC, 0xE4, 0x1E, 0x32, 0x9F, 0x47, 0xFB, 0x1B, 0xB6, 0x74, + 0x48, 0xD9, 0x1F, 0x41, 0x9B, 0x18, 0x26, 0xC8, 0xB7, 0x46, 0x65, 0x5F, 0xEB, 0x8F, 0x4A, 0x0D, 0x95, 0xE6, 0x99, 0x0D, 0xB8, 0xA4, 0xBE, 0x33, 0xC1, 0x36, 0x2F, 0xCC, 0x17, 0x1B, 0x08, 0x43, + 0x21, 0xE2, 0x2A, 0xCD, 0x06, 0x13, 0x1D, 0x2C, 0x34, 0xA0, 0x43, 0x48, 0xE4, 0x30, 0xDC, 0x78, 0x52, 0x78, 0x58, 0xBB, 0x38, 0x6B, 0xA2, 0xF4, 0xEC, 0xC0, 0xF3, 0xA0, 0x62, 0xCB, 0xDF, 0xF2, + 0xA4, 0x8F, 0x23, 0x71, 0x60, 0x58, 0x59, 0xEE, 0x81, 0xD6, 0xF8, 0xEA, 0x88, 0x6E, 0x00, 0x60, 0x66, 0x19, 0x34, 0x32, 0xAF, 0xCD, 0x97, 0x08, 0xE8, 0x38, 0x2B, 0x1C, 0xC2, 0xE8, 0x3C, 0x79, + 0x2D, 0xF4, 0xB4, 0xB9, 0xE0, 0xE0, 0x5D, 0x42, 0x34, 0x79, 0xE2, 0x54, 0xCC, 0xA4, 0xDF, 0x99, 0x90, 0x80, 0x26, 0x1D, 0x45, 0x0C, 0x3E, 0xD7, 0x33, 0x0E, 0x6F, 0xFF, 0xFF, 0x5E, 0x6D, 0x6C, + 0x89, 0x37, 0x20, 0xD3, 0x1B, 0x4E, 0x83, 0xB5, 0x14, 0x80, 0x5B, 0xFF, 0x76, 0x58, 0x6B, 0x63, 0x05, 0xD7, 0xBE, 0x0A, 0x96, 0xD7, 0x4F, 0x2B, 0x86, 0xC9, 0x74, 0xED, 0x21, 0x0F, 0x5C, 0xF7, + 0xFF, 0xAD, 0xE8, 0x54, 0x53, 0xA9, 0xFA, 0x1B, 0xF3, 0x40, 0xBD, 0x0B, 0xD8, 0xA5, 0xAC, 0x15, 0x2B, 0xE5, 0x59, 0x8D, 0x77, 0xB0, 0x08, 0x15, 0x22, 0x66, 0xA0, 0x1E, 0xFE, 0x20, 0x61, 0x5D, + 0xC2, 0x51, 0x48, 0x4D, 0xF4, 0xCF, 0xF5, 0xF5, 0x71, 0xA7, 0x32, 0xDA, 0x1A, 0x9E, 0xD8, 0x9F, 0x6C, 0x44, 0x61, 0x7F, 0x32, 0x72, 0xA0, 0xF4, 0xE7, 0x27, 0x58, 0x18, 0x6B, 0xD4, 0xDC, 0xA1, + 0xB4, 0xA4, 0x5D, 0xBA, 0x23, 0x2A, 0xE7, 0xF2, 0x21, 0x48, 0xA4, 0x95, 0xBC, 0xEA, 0x2E, 0xC3, 0x76, 0x1D, 0x1E, 0x06, 0x10, 0x3B, 0xCC, 0xE3, 0x6F, 0xAC, 0x74, 0xBD, 0x2F, 0x8E, 0x42, 0xAF, + 0xBB, 0xE8, 0x0B, 0x25, 0xDC, 0xB8, 0x09, 0xD4, 0x4E, 0xF9, 0x5D, 0xBF, 0x7F, 0x1A, 0x96, 0x5E, 0xDA, 0xF9, 0x89, 0xAF, 0xA3, 0xBB, 0xF4, 0x9C, 0x2F, 0xEA, 0x9E, 0xE2, 0x09, 0xE8, 0xF1, 0x17, + 0x8F, 0x5D, 0x01, 0x8B, 0xF9, 0xC0, 0x15, 0xC4, 0x51, 0x12, 0xEC, 0x17, 0xAE, 0x38, 0x0B, 0x09, 0xB2, 0x31, 0xE0, 0x15, 0xFF, 0xE2, 0xC3, 0x50, 0x48, 0x1A, 0xA8, 0xE1, 0x1B, 0x2B, 0xB5, 0x9A, + 0x25, 0x1B, 0x0D, 0xEA, 0x0D, 0x30, 0x79, 0xF0, 0x40, 0xF3, 0x3B, 0x6A, 0x6C, 0xCE, 0x48, 0xB6, 0xAB, 0x24, 0x00, 0x8A, 0xAB, 0xE1, 0x81, 0xE3, 0x1B, 0x55, 0x3A, 0xE4, 0x95, 0xB0, 0xFD, 0x76, + 0xA1, 0x3E, 0x07, 0x62, 0x0A, 0x72, 0x4B, 0x25, 0x6E, 0x34, 0x4F, 0x0B, 0x54, 0x1A, 0x57, 0x46, 0x0F, 0x6A, 0x75, 0x27, 0xC8, 0x26, 0xA4, 0x63, 0x67, 0x53, 0xB7, 0xDE, 0xD6, 0x28, 0x48, 0xDB, + 0x83, 0xDC, 0xE4, 0xBD, 0x08, 0x54, 0xD9, 0x98, 0x1D, 0x38, 0xA9, 0x63, 0xC6, 0xC7, 0x87, 0xF3, 0xE1, 0x82, 0x6B, 0xF6, 0xDA, 0x44, 0xD9, 0x5A, 0x31, 0x55, 0xB0, 0x3D, 0xA5, 0xC9, 0xA4, 0x27, + 0xCF, 0x6A, 0xD3, 0x6B, 0x6D, 0x67, 0x6F, 0x0D, 0xF8, 0x21, 0x10, 0x61, 0xFE, 0x33, 0x23, 0xF3, 0x20, 0x37, 0x74, 0x78, 0x70, 0x04, 0x36, 0xD9, 0xFE, 0xEC, 0x76, 0xF8, 0x10, 0xFE, 0x20, 0xBC, + 0xA5, 0xD0, 0xBA, 0xBB, 0xD0, 0x2E, 0xD8, 0xA3, 0x8B, 0xA4, 0x28, 0x04, 0x49, 0x20, 0xFE, 0x0C, 0x68, 0xDC, 0x6A, 0xDE, 0x9F, 0xA6, 0xE3, 0x97, 0x68, 0x0C, 0x03, 0xED, 0x81, 0x5F, 0x68, 0x48, + 0x59, 0xE6, 0x7C, 0xFA, 0x06, 0x37, 0xBE, 0x55, 0x56, 0xF9, 0x5F, 0x27, 0x0D, 0x5E, 0xC9, 0x1C, 0x64, 0x42, 0x94, 0xCB, 0xA9, 0x65, 0xDF, 0xD9, 0x61, 0x71, 0x3E, 0xCE, 0x53, 0x32, 0x8D, 0x99, + 0x17, 0xB1, 0xCE, 0xF8, 0x9C, 0xF1, 0x7B, 0x9F, 0x5B, 0x65, 0x57, 0x49, 0xD8, 0x6C, 0x10, 0x95, 0x63, 0x7B, 0xAD, 0x53, 0x2A, 0xFC, 0x5B, 0x39, 0xF3, 0xDA, 0xA0, 0x1F, 0x74, 0x0C, 0xBF, 0x49, + 0xF7, 0x57, 0x0F, 0x4B, 0xDC, 0xF1, 0x92, 0x41, 0xB6, 0x14, 0x9C, 0x8C, 0xF2, 0x49, 0x2B, 0x02, 0x57, 0xCA, 0x67, 0xC3, 0x95, 0xEC, 0xB1, 0x9C, 0x04, 0x95, 0x9A, 0x85, 0x93, 0x79, 0xB6, 0x54, + 0xDB, 0x7B, 0x67, 0xCC, 0xB7, 0xAE, 0x99, 0xDA, 0x88, 0xC1, 0x84, 0x1F, 0xD6, 0xEE, 0x6E, 0xA5, 0x21, 0xA6, 0x06, 0x9E, 0x64, 0x26, 0xD3, 0x82, 0xF8, 0x8C, 0xD2, 0x57, 0x17, 0xD8, 0x04, 0x51, + 0xD1, 0xA8, 0xF1, 0x09, 0x7D, 0xA5, 0xD7, 0x15, 0x28, 0xF4, 0x48, 0xF3, 0x72, 0xA2, 0x25, 0x53, 0x60, 0x62, 0x67, 0x85, 0x8E, 0x1C, 0x9D, 0xEF, 0x6F, 0x45, 0x66, 0x98, 0x5C, 0xDE, 0xC3, 0x17, + 0xCD, 0xCE, 0x2D, 0x59, 0x56, 0x08, 0x66, 0x86, 0xFA, 0x9E, 0xDC, 0x49, 0xDB, 0xEB, 0xF2, 0x60, 0xEB, 0x23, 0xB8, 0x57, 0x3B, 0x98, 0x07, 0x6E, 0x4B, 0x11, 0xA7, 0x13, 0xE7, 0x24, 0x78, 0xD2, + 0x0D, 0x10, 0xE9, 0xE9, 0x20, 0xB1, 0xFC, 0xC5, 0x62, 0xE0, 0x8F, 0x9A, 0xB7, 0xA6, 0xDB, 0x96, 0x00, 0x58, 0xD7, 0x99, 0x30, 0x31, 0x53, 0xB1, 0x3D, 0x2F, 0xC2, 0x54, 0x47, 0x07, 0x46, 0x92, + 0xD6, 0xD4, 0x6F, 0x8B, 0x5C, 0x7C, 0xE9, 0xF6, 0x17, 0xDC, 0x28, 0x13, 0x58, 0xF9, 0xF1, 0x0E, 0x26, 0x87, 0xDA, 0x06, 0x54, 0x1B, 0x50, 0xD1, 0x05, 0x06, 0xBA, 0x3A, 0xF2, 0x98, 0x75, 0x5A, + 0xA1, 0xB4, 0x7D, 0x8D, 0x56, 0x13, 0x5E, 0xCA, 0xFE, 0xD1, 0xD1, 0xCD, 0xE7, 0xD5, 0xBF, 0xD0, 0x9E, 0x37, 0xB4, 0x64, 0x9B, 0xFE, 0x06, 0x55, 0x7B, 0x4E, 0x86, 0xF9, 0x04, 0xD3, 0xA8, 0xCB, + 0x7F, 0x28, 0x21, 0x71, 0x57, 0xA8, 0x3C, 0x5E, 0x04, 0x2D, 0x19, 0xC1, 0x2D, 0x8E, 0xD0, 0x9D, 0x68, 0xB2, 0xAB, 0x73, 0x07, 0xBB, 0x6C, 0xAF, 0x63, 0x9B, 0x3A, 0xEE, 0xB5, 0x13, 0xD3, 0x3C, + 0xEE, 0x09, 0x8D, 0x6D, 0xD0, 0x36, 0x0C, 0x83, 0x2C, 0x3B, 0x7B, 0x18, 0x3D, 0xB5, 0xE7, 0xFD, 0xB4, 0x55, 0x8D, 0x93, 0x3E, 0x56, 0x10, 0xBC, 0x2A, 0x08, 0x2E, 0x16, 0x9E, 0x04, 0xFE, 0x34, + 0x1B, 0x07, 0x84, 0xAE, 0xB5, 0x29, 0x10, 0xE7, 0xA2, 0x01, 0x82, 0x0F, 0x6B, 0x3C, 0x57, 0x2B, 0x37, 0x74, 0xF2, 0x9A, 0x7B, 0xF1, 0x61, 0xAC, 0xBA, 0xBE, 0x5F, 0x0B, 0x14, 0xB3, 0xC1, 0xDE, + 0x8D, 0x8F, 0xBB, 0x20, 0x5E, 0xE7, 0x40, 0x0A, 0x06, 0x81, 0xF7, 0x98, 0x52, 0xE6, 0xBF, 0x1B, 0x5A, 0x50, 0x33, 0xD9, 0x04, 0x01, 0x47, 0xE0, 0x64, 0xDC, 0x10, 0xEA, 0xC0, 0x42, 0x11, 0x0C, + 0x43, 0x09, 0x2D, 0xD4, 0x40, 0x2B, 0x64, 0x58, 0x4A, 0x81, 0xD6, 0xD2, 0x11, 0xD4, 0x00, 0x8E, 0xE1, 0xF1, 0x9E, 0xB0, 0x0E, 0x84, 0xDC, 0x3A, 0x3D, 0xBE, 0x22, 0x1A, 0xE8, 0x6E, 0xAC, 0xAE, + 0xA6, 0x83, 0x24, 0xD2, 0xF1, 0xA5, 0x73, 0x0F, 0x03, 0x32, 0xEA, 0xD6, 0x4F, 0x02, 0xB9, 0xB5, 0x97, 0x09, 0xF1, 0x51, 0x03, 0xE2, 0x6D, 0x89, 0x71, 0xB7, 0xB6, 0xDB, 0xCF, 0xC8, 0x75, 0x04, + 0xFE, 0xB0, 0x0E, 0xD4, 0x1A, 0x02, 0x78, 0x9E, 0xB9, 0x79, 0xE2, 0xCB, 0xF7, 0x47, 0x26, 0x89, 0x64, 0xAB, 0xC8, 0x41, 0x2A, 0x53, 0x93, 0x70, 0xBF, 0x52, 0x0D, 0x9A, 0xAE, 0xF9, 0x29, 0xE8, + 0xBA, 0xFD, 0x8E, 0x18, 0x5B, 0xE2, 0xAA, 0xB0, 0x40, 0xA7, 0x7A, 0x7B, 0xF6, 0x80, 0x7F, 0x0A, 0x8A, 0x41, 0xAC, 0x61, 0x89, 0xBF, 0x00, 0xAB, 0xC7, 0x7C, 0x62, 0x05, 0x17, 0xBE, 0xAF, 0xBF, + 0x0A, 0x63, 0x05, 0x8D, 0x8D, 0x47, 0x8F, 0xCB, 0xC4, 0x2C, 0x6A, 0x77, 0x83, 0xC7, 0x69, 0x51, 0x6F, 0x24, 0x06, 0xD4, 0x4C, 0x23, 0x52, 0x99, 0xBF, 0x2E, 0x4E, 0x1C, 0xFF, 0xB7, 0xBE, 0xA0, + 0x04, 0x0C, 0x94, 0x58, 0xA1, 0xC7, 0x74, 0x18, 0x63, 0x66, 0xC1, 0x17, 0x4B, 0x04, 0xB5, 0x43, 0xF7, 0x2B, 0xD5, 0x4A, 0x30, 0xFF, 0x99, 0x47, 0xE8, 0x2E, 0x90, 0x47, 0x4C, 0xDD, 0xC6, 0xF0, + 0x69, 0xB4, 0x1F, 0xC7, 0x68, 0xB8, 0x0A, 0x02, 0xED, 0x29, 0xC8, 0x30, 0xAD, 0x27, 0xCD, 0xFC, 0x68, 0x6C, 0x64, 0x6A, 0xEA, 0x27, 0x9B, 0x22, 0xE6, 0x09, 0x2E, 0xD3, 0xA1, 0x72, 0x72, 0x19, + 0xB2, 0x81, 0xE9, 0x72, 0xF5, 0x0C, 0x88, 0x66, 0xF4, 0x4E, 0x19, 0x8B, 0x0F, 0x24, 0xFF, 0xA6, 0xA7, 0x39, 0x5D, 0x1E, 0x41, 0x05, 0x84, 0x2A, 0x60, 0xE0, 0x17, 0x35, 0x50, 0x48, 0x1C, 0x64, + 0x12, 0xF6, 0xB5, 0xAE, 0x7F, 0xF6, 0x54, 0xFD, 0x43, 0xC0, 0xD6, 0x7E, 0x8A, 0x65, 0xB6, 0x6D, 0x6D, 0x52, 0x47, 0xD6, 0xB1, 0xD5, 0xC6, 0x60, 0xCB, 0xAC, 0xF2, 0xCB, 0xDF, 0x0D, 0x81, 0xA1, + 0x68, 0xED, 0x6C, 0x82, 0x7D, 0xDC, 0xDB, 0xA0, 0xAF, 0x5B, 0xF2, 0x50, 0x42, 0x72, 0x85, 0xF3, 0x0F, 0x5C, 0x6D, 0x20, 0xED, 0x03, 0x47, 0x20, 0x33, 0x76, 0x4F, 0x2B, 0x19, 0x88, 0x4F, 0x66, + 0x2D, 0x45, 0x45, 0xBA, 0x21, 0x89, 0xD2, 0xA2, 0xA3, 0xC2, 0x9F, 0x4E, 0x89, 0xD5, 0xF5, 0x5E, 0xC6, 0xDC, 0x8E, 0x49, 0x7B, 0xA6, 0x75, 0xFE, 0x22, 0x42, 0xDA, 0x34, 0x80, 0x8C, 0x8D, 0xA5, + 0xD0, 0xE5, 0x68, 0xE7, 0x86, 0x91, 0x96, 0xCB, 0x45, 0x9D, 0x6B, 0x65, 0xA2, 0x77, 0x82, 0x0F, 0x7D, 0xD7, 0x8A, 0x31, 0xA5, 0x3B, 0x2F, 0xE7, 0x02, 0x1C, 0x9F, 0x51, 0xBB, 0x63, 0x41, 0xCB, + 0xE3, 0xCF, 0xA5, 0xF6, 0x89, 0xB8, 0xE5, 0x4F, 0x00, 0x28, 0x51, 0x71, 0x4B, 0xAA, 0x8D, 0x2D, 0x8E, 0xF9, 0x13, 0xDB, 0x9A, 0x14, 0x4B, 0x6F, 0xF6, 0x6A, 0xEC, 0x4C, 0xEF, 0x06, 0xE9, 0xD2, + 0x73, 0x49, 0x60, 0xD7, 0xFA, 0xEC, 0x0E, 0x64, 0x2D, 0xC5, 0x69, 0xCA, 0xFA, 0xB3, 0xA9, 0x32, 0x08, 0x81, 0xAE, 0xAF, 0xF8, 0x02, 0x72, 0x36, 0x18, 0xB5, 0x77, 0x69, 0x1C, 0x93, 0x72, 0x02, + 0x1D, 0x40, 0x92, 0xE0, 0xBD, 0x91, 0x3D, 0x38, 0xD7, 0x69, 0x55, 0xAA, 0x79, 0x2A, 0x85, 0x20, 0x2B, 0x5A, 0x90, 0x62, 0xD9, 0x7F, 0xE6, 0x57, 0x45, 0xD8, 0xC5, 0x50, 0xCF, 0xD0, 0xD4, 0x18, + }, + .t1_len = 2560, + .t1 = { + 0x2C, 0xAF, 0xB7, 0x2F, 0x71, 0x55, 0x72, 0xBF, 0x43, 0x28, 0x38, 0xE0, 0x80, 0xCA, 0x4A, 0x19, 0x8A, 0x28, 0x4B, 0xBD, 0xF0, 0xC4, 0x54, 0xF0, 0x94, 0x5E, 0x95, 0x3D, 0xD0, 0x71, 0x99, 0xD2, + 0xC6, 0x21, 0x0E, 0x59, 0xE6, 0xED, 0x17, 0x7D, 0xA8, 0xF0, 0xBB, 0x19, 0xEF, 0x02, 0x9E, 0x6F, 0xDB, 0x3B, 0xAC, 0x91, 0x00, 0x13, 0x11, 0x60, 0x51, 0x8B, 0xB2, 0xA8, 0x85, 0x56, 0xA8, 0xF4, + 0x8A, 0xA1, 0x97, 0x23, 0x6B, 0x4F, 0x00, 0x46, 0x78, 0x6C, 0xF0, 0xD2, 0x37, 0x4D, 0xA1, 0x9A, 0x5D, 0xF8, 0x0B, 0x19, 0xB1, 0x3D, 0xB3, 0x33, 0xB0, 0xD3, 0x0D, 0x7B, 0x1C, 0xE8, 0xD8, 0x1F, + 0x71, 0x66, 0xB0, 0x5E, 0x0E, 0x45, 0x67, 0x02, 0x92, 0x34, 0x83, 0x41, 0xCE, 0xF0, 0xCF, 0xEC, 0xB2, 0xC6, 0x1F, 0xAE, 0x5B, 0x5E, 0x8C, 0x05, 0x3E, 0xB2, 0x94, 0x71, 0xE1, 0x79, 0xA2, 0x1F, + 0x0D, 0xDF, 0x15, 0xB7, 0xA9, 0xF2, 0x8C, 0xF3, 0x58, 0x0F, 0x7D, 0x0E, 0xBA, 0x06, 0xE7, 0x22, 0x67, 0xEB, 0xBA, 0x35, 0xAB, 0xDC, 0xD3, 0x12, 0xBD, 0x3B, 0xBE, 0x6A, 0xC8, 0xEF, 0x24, 0x64, + 0xD0, 0xB4, 0xBC, 0xA5, 0x44, 0x16, 0x7A, 0xF7, 0x53, 0x19, 0x5B, 0x40, 0x57, 0x00, 0x27, 0x3A, 0xDB, 0xAF, 0x24, 0x5F, 0x73, 0x3B, 0x1F, 0xD7, 0x74, 0xBC, 0x5D, 0xE7, 0x7C, 0xE2, 0xD8, 0x27, + 0x2B, 0xCF, 0x6F, 0x99, 0xCC, 0x2C, 0xB2, 0x3E, 0x08, 0x27, 0xA0, 0x2F, 0x3F, 0x0F, 0xCA, 0x3B, 0xEC, 0x62, 0x22, 0xAE, 0xFC, 0x76, 0x22, 0x52, 0x5D, 0x86, 0xF7, 0x59, 0xF5, 0x19, 0xE4, 0xCE, + 0xD5, 0x5B, 0x93, 0xD5, 0x6E, 0xA1, 0x09, 0x18, 0x2F, 0x0A, 0x75, 0x65, 0xD9, 0xF8, 0x4D, 0x74, 0x6A, 0x9A, 0x32, 0xB4, 0x42, 0x7B, 0xF6, 0x92, 0x99, 0x53, 0x36, 0x63, 0x37, 0xAE, 0x46, 0xCF, + 0x78, 0xAB, 0xE2, 0x11, 0x92, 0xBD, 0x6A, 0x6C, 0x90, 0xAC, 0x8D, 0xAD, 0x66, 0xBF, 0x71, 0x37, 0x48, 0xC1, 0xA3, 0xE6, 0x73, 0x7D, 0xB3, 0x93, 0xB0, 0x18, 0x6C, 0xEA, 0x9D, 0x0E, 0xBA, 0x62, + 0x47, 0xB9, 0x0C, 0x94, 0x32, 0x86, 0xED, 0x0E, 0x13, 0x4C, 0xF2, 0x89, 0x27, 0xA3, 0x29, 0xD3, 0x56, 0x45, 0x5A, 0x6E, 0x56, 0x5D, 0x14, 0xDD, 0xDF, 0x5F, 0xA7, 0x0B, 0xF3, 0xAD, 0x13, 0xF4, + 0xEE, 0x51, 0x65, 0x8A, 0x92, 0x38, 0xCB, 0x97, 0x90, 0x24, 0xE5, 0x8D, 0x64, 0xF3, 0x79, 0x6F, 0x4C, 0xE3, 0x7C, 0x23, 0xF1, 0x0E, 0x44, 0x1F, 0x50, 0xD9, 0x76, 0x38, 0x8C, 0x6D, 0xEC, 0xED, + 0x8E, 0xD9, 0x35, 0xD2, 0xC6, 0xC6, 0xBB, 0x12, 0xC6, 0x12, 0xAF, 0xB7, 0xA0, 0x2D, 0x91, 0x34, 0x26, 0xB6, 0xAE, 0x22, 0x39, 0x00, 0x4E, 0xEC, 0x58, 0xAD, 0xA2, 0xFE, 0x3C, 0x67, 0xC4, 0xE2, + 0xA9, 0xF0, 0x3E, 0x49, 0x03, 0x50, 0xFC, 0x47, 0x18, 0xF3, 0x6A, 0x86, 0x1D, 0x93, 0xD2, 0x47, 0x3C, 0xCB, 0x31, 0xB7, 0xF1, 0xD7, 0xAD, 0xAE, 0xD5, 0xE0, 0xCE, 0x6A, 0xA9, 0x38, 0x18, 0x57, + 0x9E, 0x15, 0x71, 0x27, 0x19, 0x0A, 0xB4, 0x08, 0x40, 0x20, 0x40, 0x4C, 0x61, 0xC2, 0xE5, 0xC6, 0x78, 0xDC, 0x37, 0xCB, 0x53, 0x65, 0x40, 0xA4, 0x3F, 0x5C, 0xC6, 0x99, 0xDC, 0x40, 0x95, 0xFE, + 0x03, 0xFB, 0x7C, 0xEC, 0x5E, 0xFD, 0x3D, 0x9C, 0x87, 0x50, 0x32, 0xDF, 0x94, 0x57, 0x16, 0x46, 0x2B, 0xA3, 0xAE, 0x6D, 0xBF, 0x6C, 0x5B, 0xC8, 0x99, 0xAB, 0x8A, 0x7C, 0x59, 0xC5, 0xF6, 0x6B, + 0x74, 0x78, 0xB1, 0x61, 0xF4, 0x22, 0x98, 0x6C, 0xDA, 0x91, 0xD0, 0x8B, 0xE7, 0x58, 0x49, 0x4B, 0xA1, 0x75, 0x9B, 0x1E, 0x05, 0x7E, 0x31, 0xA4, 0x15, 0xD7, 0x0A, 0xCC, 0xC0, 0x80, 0xC7, 0x6D, + 0x6C, 0x32, 0x09, 0x9C, 0xF7, 0x45, 0xAC, 0x61, 0xCC, 0x42, 0xA9, 0x6E, 0x59, 0x4F, 0x3D, 0x78, 0x76, 0x98, 0x31, 0x3D, 0x62, 0xAD, 0x6C, 0xD4, 0x6A, 0xF5, 0x90, 0x66, 0xE1, 0xE5, 0xCA, 0x9F, + 0x83, 0xC7, 0xE5, 0xC6, 0x8C, 0xAE, 0x2D, 0x63, 0x2C, 0xF4, 0xF6, 0xA1, 0x7A, 0xA8, 0x0F, 0xF5, 0x34, 0x97, 0xB6, 0xFE, 0x50, 0xB3, 0xE6, 0x21, 0x5C, 0x2F, 0xE4, 0x65, 0x7B, 0xB1, 0xE2, 0x56, + 0x94, 0xE0, 0x79, 0x7E, 0xA4, 0x0E, 0x95, 0x75, 0x8B, 0xE6, 0x8E, 0xF3, 0x0E, 0xB9, 0xE3, 0xF5, 0xB6, 0xAF, 0xFF, 0x45, 0xA7, 0x7D, 0xAC, 0xD0, 0xEA, 0xB5, 0xC1, 0x03, 0x14, 0xE3, 0x1B, 0x6C, + 0xDF, 0x85, 0xF4, 0x74, 0x1B, 0xFF, 0xE6, 0xD0, 0x1C, 0xE2, 0xA2, 0xB9, 0xC3, 0xDF, 0x0A, 0xE8, 0x7A, 0x4A, 0x7A, 0x99, 0x02, 0xBC, 0xA1, 0x24, 0x90, 0xDC, 0x27, 0x9B, 0x81, 0xC0, 0x37, 0xA4, + 0xF9, 0xE8, 0xAF, 0xB9, 0xC9, 0xD8, 0x52, 0x4F, 0x84, 0x7D, 0xED, 0xF8, 0x0C, 0x41, 0xBB, 0xE2, 0x36, 0xCC, 0x0D, 0x1C, 0xD7, 0x9D, 0x46, 0x3B, 0xFF, 0x96, 0xCD, 0x7C, 0x31, 0x87, 0x95, 0x24, + 0x76, 0x32, 0xAB, 0x01, 0xA1, 0xF0, 0x52, 0xF4, 0xF7, 0x30, 0xDD, 0xD1, 0x7B, 0xD1, 0x0A, 0xBF, 0x36, 0x34, 0x41, 0x52, 0xD5, 0xB8, 0x41, 0x15, 0x5B, 0x71, 0x79, 0x2B, 0xB4, 0x1F, 0x5C, 0x9E, + 0x33, 0x16, 0x5D, 0x3D, 0xCE, 0x8E, 0xA5, 0xFE, 0xFE, 0xC6, 0x3F, 0xAD, 0x10, 0x8B, 0x26, 0xC0, 0xC3, 0x77, 0x33, 0x92, 0x57, 0x0D, 0x13, 0x6D, 0x67, 0xFC, 0xEF, 0xC7, 0x10, 0x8D, 0x1E, 0x9D, + 0x99, 0x30, 0x2B, 0xD5, 0x78, 0x45, 0x33, 0xD5, 0x62, 0x44, 0xE0, 0x12, 0x67, 0x54, 0x0F, 0x5D, 0x06, 0xC1, 0xD4, 0xCA, 0xF6, 0x5B, 0x4E, 0xAA, 0x67, 0x38, 0x51, 0x48, 0xCB, 0xD1, 0xC7, 0x3E, + 0xAD, 0x46, 0x74, 0x31, 0x9A, 0xBF, 0x03, 0x14, 0x03, 0x05, 0x4A, 0x39, 0x05, 0x49, 0x52, 0x48, 0x47, 0xE6, 0x9C, 0x93, 0x29, 0x40, 0x22, 0x0C, 0xB6, 0xFC, 0x18, 0xE0, 0x6F, 0x11, 0x29, 0x89, + 0xA2, 0x37, 0xAB, 0x7F, 0x3B, 0x65, 0x41, 0xF6, 0x99, 0xE0, 0x2F, 0x71, 0x43, 0x53, 0x99, 0x59, 0x15, 0xFF, 0xB7, 0x34, 0xC6, 0xC0, 0xB7, 0x15, 0x0D, 0x5D, 0xD4, 0xB1, 0x72, 0x83, 0x6F, 0x7A, + 0x75, 0xD1, 0x0C, 0x58, 0xCE, 0x5F, 0x68, 0x62, 0x1F, 0x2C, 0x6C, 0xB6, 0xDC, 0x49, 0xF1, 0x14, 0xCE, 0x55, 0x6C, 0xDB, 0xF5, 0xF4, 0x73, 0x91, 0x21, 0x2F, 0x1B, 0xCB, 0xFB, 0xB4, 0xAA, 0x7C, + 0x99, 0x27, 0x80, 0xFC, 0x51, 0x2D, 0x21, 0x5E, 0xCC, 0xB1, 0x60, 0x52, 0x4E, 0x4E, 0xAC, 0x73, 0x8A, 0x04, 0x83, 0x0A, 0xE4, 0x11, 0xA0, 0x9D, 0xFC, 0xEE, 0x5D, 0xEF, 0x02, 0xC9, 0x75, 0xD2, + 0xCD, 0x08, 0x88, 0xAD, 0x16, 0xA2, 0xDF, 0x46, 0x99, 0xD5, 0xE7, 0x10, 0xFF, 0xFC, 0x45, 0xF0, 0x2C, 0x4C, 0xC9, 0xD9, 0x64, 0x7F, 0x1A, 0xAC, 0x14, 0x06, 0x00, 0x12, 0x23, 0xFE, 0x56, 0x4D, + 0xD5, 0xA4, 0x3C, 0xBA, 0xAE, 0xFE, 0xD2, 0xBC, 0x94, 0x4F, 0x1C, 0x10, 0x8A, 0x8C, 0x2D, 0xA4, 0x48, 0x53, 0xFF, 0xE8, 0x38, 0x4A, 0x07, 0x4D, 0xD7, 0x26, 0x96, 0xDC, 0x68, 0x3F, 0x64, 0x48, + 0x17, 0x4B, 0xF0, 0x4B, 0x6A, 0x4F, 0x8A, 0x09, 0xE8, 0x21, 0xDC, 0xD4, 0xEF, 0x92, 0xB4, 0xDC, 0x54, 0x0C, 0x7C, 0x46, 0x54, 0x53, 0x67, 0x37, 0x33, 0x2B, 0xE9, 0x61, 0xC0, 0xD9, 0xBA, 0xC6, + 0xC4, 0x4C, 0xE8, 0x78, 0x92, 0x94, 0x2E, 0xA4, 0xE6, 0x81, 0xD7, 0xAB, 0x65, 0xAB, 0x2F, 0xCA, 0x41, 0x83, 0x7E, 0x0F, 0x45, 0x5F, 0x4E, 0x55, 0xC9, 0xE5, 0x11, 0xA7, 0xD9, 0xD7, 0x60, 0x25, + 0xA7, 0x9B, 0x43, 0x45, 0x6F, 0xEA, 0x7F, 0xB3, 0x49, 0x2E, 0xF8, 0xAA, 0x06, 0x9C, 0x46, 0x8C, 0xF7, 0x4D, 0x02, 0xA6, 0xB5, 0x52, 0xD1, 0xB8, 0xA1, 0x44, 0x18, 0x8C, 0xD6, 0x8A, 0x8A, 0x60, + 0x99, 0x85, 0xAB, 0x62, 0xD1, 0xCC, 0xBC, 0xCA, 0x7E, 0xFF, 0x91, 0xDE, 0x5C, 0xC6, 0xE0, 0x80, 0x1D, 0x04, 0xE3, 0x30, 0x93, 0xEB, 0x70, 0x49, 0x8E, 0xA8, 0xCB, 0x05, 0x06, 0x18, 0xB2, 0x72, + 0xAF, 0x06, 0x2D, 0xD4, 0xDC, 0x10, 0x9C, 0x19, 0xC8, 0x63, 0xAA, 0x59, 0xF5, 0xB8, 0xAF, 0x74, 0x42, 0xBD, 0xA3, 0xE4, 0x11, 0xCE, 0x36, 0xD1, 0x44, 0xD6, 0xCD, 0x3F, 0x57, 0x2F, 0x1C, 0xFE, + 0x67, 0x26, 0x98, 0xB0, 0xC0, 0x74, 0x3B, 0xCE, 0xD7, 0x32, 0x9A, 0xDB, 0x98, 0x45, 0xCA, 0xFF, 0x6C, 0x10, 0xB2, 0x6C, 0x32, 0x51, 0x6F, 0x9E, 0x53, 0x8C, 0x83, 0x0B, 0x61, 0x62, 0x7D, 0x68, + 0xEA, 0x76, 0x8D, 0xD0, 0x3E, 0x98, 0x0B, 0x40, 0x2B, 0x76, 0x59, 0xEA, 0x65, 0x66, 0xD7, 0x36, 0xF7, 0x88, 0x1A, 0x8D, 0x0E, 0x42, 0xA8, 0xCA, 0x24, 0x7E, 0x51, 0x29, 0xB0, 0x28, 0x92, 0x5B, + 0xE7, 0x53, 0xC3, 0x91, 0xD7, 0x75, 0x03, 0x5A, 0x44, 0x69, 0x6E, 0x26, 0xF8, 0xA6, 0x48, 0x7C, 0x7C, 0x8D, 0xE7, 0xD0, 0x49, 0x22, 0xB8, 0x75, 0xCC, 0xD3, 0xD2, 0x12, 0x11, 0x66, 0xC3, 0x34, + 0x6B, 0x51, 0xD5, 0xD5, 0x43, 0x76, 0x53, 0xCC, 0xDB, 0xDF, 0x49, 0x85, 0x65, 0xB1, 0xBF, 0x1B, 0xDF, 0x91, 0x82, 0xC4, 0x3B, 0x15, 0x4B, 0x00, 0xC0, 0x42, 0x48, 0x00, 0xB6, 0xA8, 0xE9, 0x64, + 0xF4, 0x37, 0xD3, 0xDF, 0xA6, 0xA6, 0x48, 0x20, 0x0D, 0xC0, 0xE0, 0x7D, 0xD2, 0xDA, 0x98, 0x19, 0xFC, 0xF2, 0xB2, 0x25, 0x8E, 0x07, 0xF0, 0xC5, 0x0A, 0xF4, 0x43, 0x30, 0x43, 0x5B, 0x23, 0x48, + 0xB7, 0x4C, 0xCC, 0x5F, 0x24, 0xE5, 0xDC, 0xCF, 0x67, 0xB0, 0x63, 0xDB, 0x59, 0x70, 0xBC, 0x7B, 0x59, 0x04, 0x99, 0xB2, 0xDB, 0x49, 0xFB, 0x2E, 0xB3, 0xF0, 0x88, 0x3E, 0x97, 0x04, 0x20, 0x9A, + 0xFF, 0x45, 0xBF, 0xB6, 0x12, 0x70, 0xEB, 0xB1, 0x3D, 0x89, 0x14, 0x60, 0xBD, 0x5E, 0x8B, 0x5F, 0xCE, 0x07, 0x3B, 0x50, 0x82, 0xC6, 0x5B, 0x0F, 0xE3, 0x7C, 0x7D, 0xC4, 0x14, 0xCC, 0xA3, 0xEF, + 0xD1, 0x08, 0x5F, 0x58, 0x16, 0xFC, 0x71, 0x0C, 0xF4, 0x5B, 0x45, 0x5B, 0x98, 0xAE, 0x53, 0xA2, 0x4A, 0x2D, 0x92, 0x40, 0x0B, 0xCD, 0x15, 0xA0, 0xFE, 0xA7, 0x94, 0xC4, 0x63, 0xBB, 0x59, 0x15, + 0x39, 0xD1, 0x17, 0x19, 0x50, 0xCA, 0xA3, 0x47, 0x61, 0x67, 0x90, 0xCF, 0x8D, 0x22, 0xC5, 0x46, 0xE7, 0x5A, 0x6E, 0xEB, 0x72, 0x68, 0x09, 0xD0, 0xC0, 0x72, 0xFF, 0x21, 0x61, 0xA2, 0xA4, 0x41, + 0xFD, 0xF3, 0x9C, 0xAD, 0x7A, 0x18, 0xF2, 0xB0, 0xB4, 0x26, 0x1D, 0xC2, 0xD3, 0xB4, 0x17, 0xB8, 0x44, 0xAD, 0xB7, 0x1E, 0xB7, 0xE7, 0x2F, 0xE2, 0x4F, 0x8D, 0xDE, 0x92, 0xD7, 0xC4, 0xF2, 0xDA, + 0x29, 0x3A, 0xCC, 0x92, 0x23, 0xA8, 0x73, 0x3A, 0x84, 0x99, 0x65, 0x63, 0x2D, 0x77, 0x10, 0xF7, 0xA7, 0xBB, 0x87, 0x04, 0x1A, 0x3D, 0x3A, 0x51, 0x66, 0xBA, 0x90, 0x65, 0x7E, 0x03, 0xAF, 0x26, + 0xA9, 0xD1, 0x0D, 0x66, 0x19, 0x9E, 0x60, 0xEE, 0x70, 0xD3, 0xFB, 0xF3, 0x9F, 0xE4, 0x6C, 0xFC, 0x8D, 0xDC, 0x73, 0x68, 0x34, 0xE4, 0xE4, 0x05, 0xF8, 0x3C, 0xDD, 0x0C, 0xAA, 0xF8, 0x16, 0x28, + 0xC7, 0x98, 0x99, 0xEA, 0xED, 0xBF, 0x25, 0x03, 0x18, 0x77, 0xE1, 0x62, 0x67, 0x5D, 0x9C, 0x57, 0xF6, 0xA4, 0xD9, 0xFF, 0xE0, 0xFD, 0x68, 0x40, 0xF9, 0x9B, 0xEC, 0xE9, 0x06, 0x2C, 0x98, 0xE0, + 0x74, 0xBB, 0x30, 0x71, 0x76, 0xA7, 0x8C, 0x4A, 0x4D, 0xCE, 0x9E, 0x40, 0x31, 0xBD, 0x10, 0x28, 0x55, 0x39, 0xC1, 0x80, 0xF4, 0xB8, 0xBD, 0x33, 0xE8, 0xCB, 0x11, 0xBC, 0x9C, 0x1D, 0xD9, 0x37, + 0x6D, 0x73, 0xD3, 0x1D, 0x6E, 0xFE, 0x1A, 0xCC, 0x61, 0x7E, 0xC9, 0x92, 0xE3, 0x9B, 0x49, 0x6B, 0x05, 0xB1, 0x1A, 0xCA, 0xFF, 0x35, 0x6D, 0x72, 0x53, 0x7C, 0x60, 0x11, 0x0C, 0x90, 0x51, 0xD6, + 0x91, 0x7C, 0x1F, 0xFB, 0x03, 0x1B, 0x69, 0xD3, 0x9B, 0x94, 0x28, 0x85, 0x8A, 0x4B, 0xF7, 0x28, 0x83, 0xB4, 0xC7, 0x87, 0x9F, 0xEF, 0x69, 0xBF, 0xCC, 0x31, 0xA1, 0xCF, 0xB3, 0x39, 0xC5, 0x79, + 0x47, 0xFC, 0x79, 0x1B, 0xDA, 0x3E, 0x81, 0x20, 0x5D, 0x04, 0x6E, 0x1B, 0xFA, 0xB8, 0xE0, 0x45, 0x19, 0xEA, 0x65, 0x24, 0xD5, 0xFF, 0x16, 0x6D, 0x56, 0xA8, 0xB3, 0xC2, 0x02, 0xCF, 0x32, 0x5D, + 0x29, 0x76, 0x60, 0xDD, 0x94, 0x14, 0xE9, 0xD2, 0xAF, 0x1F, 0xE0, 0x11, 0xC2, 0xA1, 0x6F, 0xCE, 0x6A, 0x5B, 0x75, 0x1E, 0x7B, 0xB0, 0x55, 0xDD, 0x40, 0x23, 0x72, 0xB8, 0xDB, 0xE6, 0x43, 0xDB, + 0xAA, 0x8B, 0xAD, 0x19, 0xEA, 0x47, 0xE1, 0x4D, 0xD6, 0xC0, 0x06, 0xC8, 0x82, 0xC0, 0xCE, 0x27, 0x51, 0x82, 0xD5, 0xC7, 0x93, 0xA7, 0x24, 0x6E, 0x35, 0xA7, 0x2F, 0xA9, 0x71, 0x89, 0x48, 0xD8, + 0x9D, 0x7C, 0x70, 0x07, 0xE4, 0x65, 0x09, 0x67, 0xF0, 0x1A, 0x6C, 0xCD, 0x2F, 0x9B, 0x23, 0xD8, 0x5C, 0xB7, 0x0E, 0xAB, 0x54, 0x05, 0x96, 0xD4, 0xE7, 0xEF, 0xD3, 0xC4, 0x64, 0x26, 0x69, 0x36, + 0xCE, 0x6B, 0xCB, 0x38, 0x86, 0x4A, 0xFC, 0xC9, 0x0C, 0xA7, 0x4D, 0xED, 0xD2, 0x45, 0xDE, 0x19, 0xD8, 0x62, 0x36, 0xD8, 0xB5, 0xF2, 0xAD, 0xD8, 0xEA, 0x9B, 0xA7, 0x4C, 0x3C, 0xC9, 0x7F, 0xC9, + 0xDD, 0xE8, 0x60, 0x6F, 0xB3, 0x43, 0xCC, 0xB1, 0x98, 0x37, 0x59, 0xDB, 0x7F, 0xCD, 0x2D, 0x18, 0x7E, 0xE6, 0x42, 0xC9, 0x8B, 0x05, 0x0E, 0xB1, 0x67, 0xF0, 0x19, 0xDB, 0x78, 0x8B, 0x7E, 0x56, + 0xD5, 0xD5, 0xB4, 0xC0, 0x77, 0x0B, 0xC0, 0x96, 0x97, 0xCF, 0xA3, 0xF0, 0xC7, 0xBC, 0x6F, 0x30, 0xCE, 0xEE, 0x06, 0xC6, 0x55, 0x84, 0x85, 0xB4, 0xB6, 0x2B, 0xE0, 0x18, 0x3D, 0x79, 0x86, 0x7C, + 0x2C, 0x91, 0x04, 0xD3, 0x85, 0xC0, 0xFC, 0xEE, 0xE9, 0x4C, 0x42, 0x49, 0x01, 0x1B, 0x6F, 0x72, 0xE3, 0x7F, 0xD5, 0xE6, 0x6D, 0xCC, 0x00, 0x4F, 0x37, 0xB6, 0x76, 0x1B, 0x6C, 0xE7, 0xC4, 0xD2, + 0x08, 0x98, 0xCB, 0xC1, 0x1E, 0x19, 0xD8, 0xCB, 0x88, 0x1A, 0xCE, 0xC8, 0x3C, 0x12, 0x70, 0x4F, 0x26, 0xC1, 0x29, 0x19, 0x14, 0x08, 0x8F, 0xCE, 0x3F, 0x88, 0x05, 0xDF, 0xE5, 0x73, 0x2A, 0xA4, + 0xAC, 0xD5, 0x69, 0xDD, 0x4F, 0x80, 0x9B, 0x3A, 0xEC, 0x3B, 0x0A, 0xE8, 0xF8, 0xA4, 0xBA, 0xC2, 0x21, 0x72, 0x96, 0x6C, 0x95, 0x39, 0x15, 0x29, 0x52, 0x43, 0x8F, 0xBD, 0x34, 0xD8, 0x67, 0xC3, + 0x28, 0xCD, 0xED, 0x82, 0xAE, 0xD9, 0x64, 0x46, 0x4B, 0xAE, 0x83, 0xBC, 0xE5, 0xCA, 0xF6, 0xE7, 0xE7, 0x19, 0x0F, 0x46, 0x4B, 0xBF, 0x7C, 0x8F, 0x51, 0x58, 0xDB, 0xFA, 0x9A, 0xF4, 0x20, 0xBC, + 0xA2, 0xB3, 0xD2, 0xFE, 0x6E, 0xC6, 0x0E, 0xAB, 0xDE, 0x95, 0x86, 0x9C, 0x8A, 0x74, 0xAE, 0x6C, 0x0A, 0x18, 0x6F, 0xBF, 0x75, 0xE3, 0x3C, 0x8E, 0x87, 0x6F, 0x57, 0xD1, 0x67, 0xD5, 0xB7, 0x43, + 0x34, 0x5E, 0x21, 0x1E, 0xF3, 0x73, 0x3D, 0x0F, 0xF6, 0x07, 0x98, 0x2E, 0x60, 0xFB, 0x3C, 0x2A, 0x59, 0xEA, 0xC1, 0x67, 0x60, 0x02, 0xED, 0x1E, 0xC8, 0xD1, 0xE2, 0xE6, 0x9E, 0xD0, 0x9B, 0xD4, + 0xAB, 0xD8, 0x4B, 0xEE, 0xFA, 0xAA, 0x06, 0xFD, 0x40, 0x09, 0xF6, 0x78, 0x77, 0x85, 0x2E, 0x9E, 0x7E, 0x38, 0xA0, 0x86, 0xEC, 0xBC, 0x42, 0x4E, 0xC7, 0xBA, 0x2C, 0x7E, 0x82, 0x56, 0x9F, 0xB1, + 0xD1, 0xDE, 0xF5, 0xD4, 0x47, 0x98, 0xB2, 0x48, 0x06, 0x55, 0x3D, 0xC6, 0x92, 0x33, 0x4D, 0xA0, 0xBC, 0x09, 0xC9, 0x19, 0x19, 0x31, 0x34, 0x0C, 0xAA, 0xA9, 0xD0, 0x9E, 0x45, 0xBA, 0xFD, 0x94, + 0x62, 0xA6, 0xDD, 0xE7, 0x62, 0xB4, 0x66, 0x79, 0x6C, 0xC4, 0xAA, 0x7C, 0xA0, 0x6A, 0x3E, 0x25, 0x0E, 0xC7, 0x04, 0x4C, 0xF0, 0x93, 0x2B, 0x45, 0xE1, 0xD7, 0x81, 0xF3, 0xE3, 0xE8, 0x10, 0x5D, + 0xFB, 0x56, 0x48, 0x35, 0x04, 0xAD, 0xBB, 0xE5, 0x2A, 0xBA, 0x41, 0xF3, 0xC7, 0x13, 0x88, 0x7A, 0x94, 0x53, 0x4B, 0x92, 0xF9, 0x9D, 0x5F, 0xF7, 0x00, 0xD9, 0x57, 0x8A, 0xF2, 0xBA, 0x61, 0xEF, + 0xA3, 0x5F, 0x7D, 0xF3, 0xF0, 0xA0, 0xAD, 0x15, 0x37, 0x2C, 0xBE, 0x39, 0x2C, 0xA3, 0x07, 0x88, 0x0C, 0x28, 0xD1, 0x9A, 0xC4, 0x1F, 0x8E, 0x9A, 0x41, 0x41, 0x63, 0x0F, 0xB6, 0x49, 0x6A, 0xBB, + 0x4F, 0xAF, 0x12, 0xB4, 0xC2, 0xF9, 0x8A, 0x34, 0x0A, 0x74, 0x48, 0x3C, 0x17, 0xEF, 0x9F, 0x14, 0x7C, 0x88, 0xBA, 0x65, 0x86, 0xDD, 0xCA, 0x75, 0xC2, 0x27, 0x96, 0xBA, 0xD2, 0xE5, 0x4A, 0x42, + 0x64, 0x7A, 0x39, 0x44, 0x4F, 0xDE, 0xA1, 0x81, 0x42, 0xF0, 0x27, 0xCD, 0xA7, 0x65, 0xAD, 0x63, 0x97, 0x12, 0x5F, 0x0A, 0x52, 0xF8, 0xB5, 0xF4, 0x24, 0x84, 0xD7, 0x27, 0x88, 0x76, 0x30, 0x81, + 0x4B, 0x20, 0x80, 0xD0, 0xC8, 0xF5, 0x17, 0xBD, 0x57, 0x77, 0xC2, 0x45, 0xAD, 0xDE, 0x98, 0x59, 0x05, 0x73, 0x7D, 0x79, 0x96, 0x1D, 0x81, 0xEE, 0xB0, 0xAF, 0xB4, 0x9A, 0xAC, 0x22, 0x9F, 0x65, + 0x79, 0xDE, 0xBC, 0x47, 0xC4, 0xDC, 0xFD, 0x68, 0x63, 0x1B, 0xE8, 0x27, 0x54, 0xFF, 0x8D, 0x84, 0xF0, 0xFE, 0xA3, 0xFB, 0x2B, 0x83, 0xD2, 0xFB, 0x38, 0x4D, 0x40, 0xCF, 0xB4, 0x2E, 0xA8, 0xFF, + 0x2B, 0xC0, 0xC5, 0x5C, 0x87, 0xE4, 0xF7, 0x0C, 0x76, 0x58, 0xA5, 0x4D, 0xD2, 0xF5, 0x34, 0x22, 0xAE, 0x1F, 0xE0, 0xFC, 0x28, 0x6E, 0x8B, 0x32, 0xE9, 0xD4, 0x5C, 0x96, 0x7A, 0xF0, 0x0D, 0xAA, + 0x9C, 0x68, 0x5F, 0x78, 0x10, 0x98, 0x36, 0x65, 0xE5, 0x94, 0xFD, 0x5B, 0x77, 0x25, 0x8A, 0x06, 0x41, 0x3D, 0x5B, 0x84, 0xC8, 0x01, 0x72, 0x7A, 0xA5, 0x34, 0x71, 0xE0, 0xE8, 0x71, 0x6A, 0xB4, + 0x11, 0x0A, 0x8A, 0x05, 0x74, 0x4D, 0xA2, 0x5E, 0xA4, 0x84, 0xBD, 0x11, 0x41, 0x25, 0x3E, 0xB8, 0x7B, 0xD8, 0x67, 0x36, 0xDD, 0xE8, 0x66, 0x2F, 0x77, 0x65, 0x5F, 0x83, 0x61, 0xD4, 0xB4, 0x3B, + 0x2B, 0x4F, 0xD3, 0xC5, 0x6C, 0xF7, 0x10, 0x11, 0xDC, 0x1E, 0xD9, 0x18, 0x13, 0x4F, 0x49, 0x74, 0xB4, 0xD5, 0x60, 0x83, 0x72, 0xF1, 0xDF, 0x37, 0x84, 0xBF, 0xF9, 0xAB, 0x1C, 0xB4, 0xAF, 0x5E, + 0x53, 0x33, 0xD0, 0x44, 0x51, 0x2D, 0x7C, 0xA5, 0xB3, 0xA8, 0x2F, 0xC2, 0x91, 0x5D, 0xD5, 0x0C, 0x82, 0xA2, 0xFE, 0x52, 0x1D, 0x04, 0x73, 0x8A, 0x76, 0xB8, 0x27, 0xC8, 0xB1, 0x32, 0x75, 0x99, + 0xDE, 0xFF, 0xD2, 0x24, 0x59, 0x02, 0x53, 0xB7, 0x56, 0x66, 0xEF, 0xE4, 0x8A, 0x9C, 0x29, 0x66, 0x1F, 0x55, 0xEC, 0x36, 0x8F, 0xE0, 0x36, 0x79, 0x44, 0x95, 0xC8, 0xF6, 0xA4, 0xEE, 0x7F, 0x92, + 0xB2, 0x0C, 0x4C, 0x38, 0xFB, 0x09, 0xF9, 0x48, 0x50, 0xBC, 0x0B, 0x97, 0xC2, 0x5C, 0x1E, 0x16, 0x36, 0xD5, 0xE5, 0xAD, 0x7E, 0xF7, 0x37, 0x53, 0xA9, 0x01, 0xD8, 0x38, 0x50, 0x3A, 0x94, 0x4A, + }, + .pkcs8_len = 0, + .spki_len = 0, + .msg_len = 66, + .msg = { + 0x22, 0x5D, 0x5C, 0xE2, 0xCE, 0xAC, 0x61, 0x93, 0x0A, 0x07, 0x50, 0x3F, 0xB5, 0x9F, 0x7C, 0x2F, 0x93, 0x6A, 0x3E, 0x07, 0x54, 0x81, 0xDA, 0x3C, 0xA2, 0x99, 0xA8, 0x0F, 0x8C, 0x5D, 0xF9, 0x22, + 0x3A, 0x07, 0x3E, 0x7B, 0x90, 0xE0, 0x2E, 0xBF, 0x98, 0xCA, 0x22, 0x27, 0xEB, 0xA3, 0x8C, 0x1A, 0xB2, 0x56, 0x82, 0x09, 0xE4, 0x6D, 0xBA, 0x96, 0x18, 0x69, 0xC6, 0xF8, 0x39, 0x83, 0xB1, 0x7D, + 0xCD, 0x49, + }, + .sig_len = 4595, + .sig = { + 0x5C, 0x04, 0x77, 0x77, 0xB8, 0xEB, 0x60, 0x8F, 0x9B, 0xD9, 0x11, 0xCD, 0xF6, 0x2B, 0x8B, 0xEB, 0x36, 0x61, 0xF9, 0x3F, 0xE4, 0xE6, 0x2E, 0x9A, 0x0C, 0x4E, 0x20, 0xA8, 0x88, 0x90, 0x81, 0x2C, + 0x2F, 0xC6, 0x4D, 0xEC, 0x6A, 0x3A, 0xDB, 0x78, 0x83, 0xFA, 0x86, 0xAD, 0x62, 0xC4, 0xF0, 0x72, 0x98, 0x89, 0xEC, 0xBD, 0x7B, 0x49, 0xAC, 0x68, 0x89, 0x3C, 0xD0, 0xEE, 0x56, 0x3E, 0x08, 0x41, + 0xE5, 0x3E, 0xF9, 0xC5, 0x23, 0x69, 0xA1, 0x70, 0x42, 0x82, 0x68, 0x4F, 0xDA, 0x5C, 0x61, 0x5F, 0x3B, 0x71, 0x24, 0x3B, 0x17, 0x09, 0x85, 0xD9, 0xEB, 0x28, 0x23, 0xB0, 0xAA, 0xDE, 0xAE, 0x32, + 0x05, 0xBA, 0x95, 0x63, 0xF3, 0xAD, 0xC9, 0x04, 0x71, 0x95, 0x77, 0x9B, 0x51, 0x72, 0x02, 0x83, 0xC1, 0x88, 0x30, 0x2E, 0x0D, 0xC4, 0xE6, 0x4D, 0xA8, 0xC8, 0xE2, 0x6D, 0x1A, 0x12, 0x6F, 0x1E, + 0x23, 0x6A, 0xDA, 0x99, 0x40, 0x3E, 0x4E, 0x29, 0xDF, 0x8D, 0x52, 0x21, 0xB5, 0x18, 0x57, 0x60, 0x80, 0x7E, 0x17, 0x8E, 0x46, 0xB7, 0x59, 0x5A, 0x1E, 0x31, 0x27, 0x30, 0xDA, 0x4C, 0x10, 0xE9, + 0x6D, 0x67, 0x45, 0x84, 0x89, 0x92, 0xFA, 0xFB, 0x10, 0x12, 0x58, 0xF8, 0xFE, 0xCE, 0xFA, 0x10, 0x1C, 0xC8, 0xC1, 0x92, 0x46, 0x84, 0xA4, 0x23, 0x4A, 0xB3, 0x47, 0x56, 0xAC, 0x49, 0x61, 0xC9, + 0xAB, 0x5D, 0xF0, 0xE1, 0xC8, 0x61, 0x38, 0x0A, 0x88, 0x1F, 0xDC, 0x18, 0xA8, 0x62, 0x45, 0x67, 0x23, 0xE9, 0x4C, 0xA9, 0x54, 0xAE, 0x50, 0xF5, 0x68, 0x83, 0x34, 0x28, 0x8A, 0x93, 0xD4, 0xB7, + 0x89, 0x67, 0x3A, 0xC0, 0xBC, 0x57, 0xD8, 0x3B, 0x71, 0x04, 0xF5, 0x6E, 0x40, 0x7D, 0x2A, 0x79, 0x38, 0x31, 0xAA, 0x69, 0x87, 0x19, 0xB2, 0xED, 0xE0, 0xDE, 0x3C, 0x8D, 0x70, 0xDE, 0xAB, 0x53, + 0x79, 0x6C, 0x98, 0xF1, 0x01, 0xA3, 0x76, 0xBC, 0x48, 0x88, 0xE7, 0xF8, 0x8D, 0x9D, 0xA1, 0xBD, 0x9C, 0x0A, 0x39, 0x75, 0x5F, 0xFC, 0xB4, 0xFA, 0x96, 0x99, 0x59, 0x60, 0x17, 0x62, 0x54, 0x2A, + 0x01, 0xE6, 0xD6, 0x07, 0x9B, 0x38, 0x2A, 0xCF, 0xFC, 0xEE, 0x1F, 0x17, 0x36, 0x91, 0x6B, 0xDC, 0x57, 0xD8, 0x61, 0xC0, 0x47, 0xFD, 0xF9, 0xAB, 0x49, 0x6C, 0x2B, 0x99, 0x97, 0x0C, 0x0F, 0x1D, + 0x10, 0x70, 0xFF, 0x37, 0xEB, 0x5A, 0x5C, 0x1A, 0xF6, 0x5B, 0x87, 0x75, 0xA9, 0x13, 0x83, 0x89, 0x9E, 0xBE, 0x44, 0xB3, 0xFC, 0x98, 0x11, 0xAB, 0xE5, 0x3D, 0x74, 0xDF, 0x1E, 0x58, 0xBC, 0x0A, + 0xFC, 0xEC, 0x6D, 0xEF, 0xB3, 0xC7, 0x4C, 0xF6, 0xED, 0x4C, 0xC2, 0x13, 0x05, 0xBC, 0xD5, 0x82, 0xF0, 0xD1, 0xD5, 0x5B, 0x81, 0xF3, 0x16, 0x6E, 0x90, 0x04, 0xFF, 0x1D, 0x98, 0x98, 0x21, 0x74, + 0xB7, 0x32, 0x57, 0x6C, 0x4F, 0x08, 0x00, 0x4A, 0xA1, 0x72, 0xB6, 0xED, 0xD3, 0x59, 0xEC, 0xAB, 0x95, 0xF9, 0x77, 0x5C, 0x23, 0x2B, 0x11, 0x12, 0xFD, 0xF6, 0x65, 0xB2, 0x45, 0x10, 0x8A, 0x3C, + 0xF9, 0x57, 0xD9, 0x08, 0xEB, 0xB1, 0xFA, 0x5E, 0x38, 0x5B, 0xED, 0x36, 0xDD, 0x4A, 0xE0, 0x9C, 0xB3, 0xB4, 0x94, 0x42, 0xC8, 0x1B, 0x49, 0xA0, 0x5C, 0xE7, 0xF3, 0xB8, 0xC7, 0x1F, 0x1A, 0xE2, + 0x8E, 0xC4, 0xCD, 0xE8, 0x51, 0xA2, 0x27, 0xB9, 0x9E, 0x4A, 0xDE, 0xB4, 0x7C, 0xBB, 0x12, 0xAF, 0x98, 0xBF, 0x8E, 0x1D, 0xDA, 0x9E, 0xCB, 0x09, 0x68, 0x3A, 0x74, 0xAB, 0x05, 0x3D, 0x62, 0x78, + 0xFD, 0xEF, 0xA2, 0x19, 0x83, 0xB3, 0xD3, 0xFE, 0x23, 0x96, 0x3F, 0x1C, 0x2A, 0xD9, 0x6F, 0x46, 0x64, 0xB9, 0xDF, 0x8A, 0x4A, 0xF0, 0x98, 0x5B, 0x73, 0x1E, 0xB3, 0x3C, 0xDB, 0x49, 0x5D, 0xB1, + 0x28, 0xE5, 0xDC, 0x5B, 0x36, 0x55, 0x9E, 0xFD, 0xA1, 0x17, 0x17, 0xDD, 0xBB, 0xEC, 0x43, 0x8B, 0xC8, 0x6A, 0xE7, 0x3D, 0x7D, 0x69, 0x66, 0x81, 0xF9, 0x0E, 0x6B, 0xBC, 0x24, 0x43, 0xB6, 0xA6, + 0x23, 0x21, 0xF9, 0x26, 0xC6, 0x48, 0xC3, 0x36, 0x05, 0xAB, 0x61, 0x9B, 0x02, 0xEF, 0xFD, 0x5B, 0x48, 0x4B, 0x00, 0x45, 0x15, 0x0A, 0x47, 0x53, 0xB9, 0x22, 0x52, 0x27, 0x9E, 0xA1, 0x20, 0x4F, + 0x42, 0xF3, 0x0B, 0xB0, 0xD8, 0x2D, 0x39, 0xD5, 0x58, 0x88, 0x1F, 0xFB, 0x4C, 0xD2, 0x96, 0x75, 0x6E, 0xF2, 0x8D, 0x08, 0x71, 0x20, 0xEB, 0xD5, 0xFC, 0x1D, 0x42, 0x72, 0xBC, 0x7C, 0x75, 0xB9, + 0xBB, 0x0F, 0xC3, 0x31, 0x09, 0x51, 0xCE, 0xA4, 0x5A, 0x7D, 0x06, 0xC8, 0xDC, 0xA5, 0x9E, 0xDB, 0x6F, 0x34, 0xEE, 0xEF, 0x55, 0x60, 0xF5, 0xCF, 0xD6, 0xC3, 0x44, 0xC2, 0xEF, 0x06, 0xED, 0x7B, + 0xBA, 0x25, 0x74, 0x9A, 0x2E, 0xF5, 0x62, 0xE2, 0x9F, 0xEF, 0x5C, 0xB4, 0x7C, 0x25, 0x50, 0xAB, 0x72, 0xF3, 0xA1, 0x0D, 0x15, 0x89, 0x34, 0xB1, 0xF2, 0x69, 0x51, 0x59, 0x30, 0xD1, 0x05, 0x3E, + 0x34, 0xF2, 0xB1, 0xA6, 0x8D, 0x36, 0x94, 0xEE, 0x4B, 0xC2, 0x06, 0xD8, 0x62, 0x66, 0x58, 0x68, 0x90, 0x4C, 0xAF, 0xCD, 0x9E, 0x2D, 0xAD, 0x4B, 0x26, 0x2B, 0x2A, 0x11, 0x18, 0xEE, 0xA1, 0xFA, + 0x5B, 0xF0, 0x21, 0x88, 0xE8, 0x5A, 0x8A, 0xFE, 0xA1, 0xF8, 0xBA, 0x8E, 0x36, 0x04, 0xED, 0x67, 0xC0, 0xA8, 0xC4, 0x4D, 0x61, 0x0E, 0xCE, 0x21, 0x03, 0x3D, 0x23, 0x03, 0x4A, 0x28, 0xB9, 0xBC, + 0x3F, 0x54, 0xCE, 0x7C, 0xA6, 0x3F, 0xD0, 0xC5, 0x4E, 0xC5, 0x9A, 0x3A, 0xE6, 0xF0, 0xF0, 0x15, 0x33, 0x86, 0xC2, 0xC0, 0x8B, 0x9F, 0x22, 0xC3, 0xC9, 0x21, 0xE9, 0xB6, 0xC5, 0xF6, 0x8C, 0x95, + 0x02, 0x58, 0x4B, 0x57, 0x58, 0x92, 0xE6, 0xC1, 0x00, 0xBA, 0x24, 0x38, 0x30, 0x15, 0x75, 0x22, 0x09, 0xCD, 0x36, 0x17, 0x1A, 0x86, 0x42, 0xE1, 0xAB, 0xC1, 0x77, 0xB3, 0x99, 0x58, 0x23, 0xAA, + 0x56, 0x2D, 0xC8, 0xCE, 0xD9, 0x22, 0x08, 0x68, 0xD0, 0x98, 0x71, 0x5C, 0x2B, 0xE9, 0x9C, 0x10, 0x14, 0x3B, 0x1C, 0x47, 0x6E, 0x60, 0x73, 0x1B, 0xA5, 0x7E, 0x29, 0x36, 0x4B, 0xDE, 0xC6, 0x38, + 0x4C, 0x4F, 0xC8, 0x6C, 0x72, 0x93, 0xEC, 0xBF, 0x24, 0xED, 0xE4, 0x23, 0x1F, 0x63, 0xF4, 0xD7, 0x43, 0x0C, 0x74, 0xB4, 0x5C, 0xBC, 0xD8, 0x8F, 0xA6, 0x3C, 0xA8, 0x19, 0xE3, 0xE9, 0x82, 0x26, + 0x3F, 0xAD, 0xDF, 0xEB, 0xA6, 0xFE, 0x21, 0xB3, 0xB2, 0x43, 0x7F, 0x34, 0xF8, 0x6E, 0xB3, 0x76, 0xA9, 0x3B, 0xAF, 0x4E, 0x55, 0x51, 0x99, 0xE1, 0x29, 0x91, 0x7F, 0x6A, 0x60, 0xF0, 0x8E, 0x7E, + 0x4F, 0x38, 0x73, 0x09, 0x76, 0x94, 0x6B, 0x73, 0x7E, 0xDF, 0x30, 0x2C, 0x11, 0x45, 0x95, 0x47, 0x42, 0xD1, 0x46, 0x85, 0x43, 0x09, 0x33, 0x53, 0xBF, 0xE6, 0x64, 0x94, 0xEC, 0x60, 0x02, 0x24, + 0xAA, 0x5E, 0x76, 0x62, 0x66, 0x04, 0x3F, 0x6B, 0x8E, 0x65, 0xFB, 0x89, 0xF0, 0x85, 0x23, 0x9A, 0xD8, 0xD6, 0x69, 0x3C, 0x23, 0xFD, 0x3A, 0x6F, 0x29, 0x8C, 0x3E, 0xA0, 0xF4, 0x8C, 0x6D, 0x56, + 0x3E, 0x62, 0xFD, 0x78, 0x57, 0xD6, 0xA1, 0x1D, 0x10, 0xAF, 0x8C, 0xF3, 0x6F, 0x8B, 0x34, 0xFC, 0x60, 0x66, 0x4E, 0xCE, 0x43, 0xC0, 0xA6, 0x50, 0x3F, 0x68, 0x57, 0x7C, 0x8A, 0x7B, 0xEF, 0xA1, + 0xFF, 0x91, 0xBC, 0x51, 0x0B, 0xD7, 0xB9, 0xDA, 0xCA, 0x4A, 0xB6, 0xD4, 0x00, 0xAC, 0x2D, 0x42, 0xD7, 0x07, 0x7A, 0x23, 0xD8, 0xE2, 0xF3, 0x04, 0xE8, 0x57, 0x68, 0xC1, 0x11, 0xDC, 0xAA, 0x8B, + 0x1E, 0x8D, 0x05, 0x9A, 0x3E, 0xB2, 0x38, 0x42, 0x88, 0xC9, 0x8C, 0x0F, 0x26, 0xF9, 0xB6, 0x0F, 0x61, 0x71, 0x37, 0x25, 0x4B, 0xA0, 0x77, 0x6C, 0x27, 0x2C, 0xA2, 0x3A, 0x26, 0x81, 0x0E, 0x00, + 0x6A, 0x25, 0x43, 0xE3, 0x7B, 0x78, 0x94, 0x57, 0xFE, 0xA7, 0x30, 0x41, 0xD6, 0x55, 0xEC, 0x6B, 0xA3, 0x1C, 0xAA, 0x2C, 0xDE, 0x59, 0xD4, 0x42, 0x09, 0x6A, 0xA7, 0x10, 0xF4, 0xF5, 0x03, 0x19, + 0xA2, 0xB6, 0x2D, 0x4C, 0x28, 0xD8, 0xC8, 0x8C, 0xC8, 0xFD, 0x80, 0x8F, 0x26, 0xB6, 0xF8, 0x7C, 0x9D, 0xF4, 0x85, 0xAF, 0xC9, 0xDF, 0xC3, 0x69, 0xDE, 0x7D, 0xB6, 0xFD, 0xE5, 0x12, 0x9A, 0x36, + 0xB0, 0xFF, 0xBC, 0x30, 0x13, 0x13, 0x24, 0xDD, 0x0F, 0x33, 0x27, 0xF7, 0x6F, 0x6E, 0xFB, 0x80, 0xD7, 0x84, 0x4A, 0x13, 0x3A, 0xA8, 0x48, 0x70, 0x80, 0x16, 0x59, 0x0B, 0xB3, 0xB5, 0xA4, 0x20, + 0x63, 0xD0, 0xC3, 0xCE, 0x9F, 0x7D, 0x23, 0xD6, 0x06, 0x15, 0xAC, 0xEC, 0x34, 0x71, 0x5B, 0x80, 0xEC, 0x4B, 0xFB, 0xBE, 0x78, 0xB4, 0xC1, 0x08, 0x0D, 0xCF, 0xED, 0x7F, 0xE9, 0x08, 0xE1, 0xC7, + 0x10, 0xD2, 0x50, 0xB5, 0xA0, 0xCB, 0xBB, 0x6A, 0xCC, 0x45, 0x06, 0x59, 0xB3, 0x47, 0xC6, 0xAD, 0x16, 0xDC, 0xED, 0x0F, 0x6B, 0x6A, 0x56, 0x71, 0x4B, 0x89, 0x9D, 0x4E, 0x25, 0xE1, 0x81, 0x13, + 0x89, 0xB9, 0x41, 0x26, 0x91, 0x8E, 0x11, 0x7E, 0x62, 0xB3, 0x3F, 0xE6, 0x63, 0x6C, 0xF8, 0xA2, 0x30, 0x23, 0x24, 0x92, 0xA5, 0x8A, 0x84, 0x6F, 0x7C, 0xCC, 0xF1, 0x65, 0x60, 0xE5, 0xB2, 0x51, + 0xB4, 0x2D, 0xD6, 0xCC, 0xEC, 0xED, 0x51, 0xB2, 0x83, 0x83, 0xA4, 0x18, 0x85, 0x11, 0x13, 0x21, 0x0B, 0x8D, 0x81, 0xF7, 0xA9, 0xE5, 0x10, 0xCB, 0xBD, 0x2B, 0xAA, 0xB9, 0x29, 0xC6, 0xBA, 0x85, + 0xA1, 0x4A, 0x93, 0xAC, 0xA2, 0x3E, 0xE7, 0x7B, 0xF8, 0x96, 0x52, 0xB3, 0x59, 0x24, 0x3F, 0xEA, 0xAF, 0x9E, 0x91, 0x0D, 0xB4, 0xB9, 0xBE, 0x57, 0x01, 0xCF, 0xD4, 0xDE, 0xDC, 0xF7, 0x99, 0x41, + 0xAD, 0xF7, 0x5C, 0xB9, 0xF3, 0x5B, 0x0E, 0xC4, 0xF4, 0x65, 0x80, 0x00, 0x99, 0xA5, 0xF0, 0x96, 0x27, 0x84, 0x6B, 0xE4, 0x67, 0x08, 0x3D, 0xDD, 0x93, 0xF9, 0x44, 0xA1, 0x6A, 0xD7, 0x4B, 0x80, + 0x28, 0x5D, 0xEF, 0x16, 0x08, 0x0B, 0x2E, 0xEB, 0xD9, 0xF8, 0xE2, 0x5A, 0x5C, 0x05, 0x26, 0xFC, 0xEB, 0xD9, 0x8E, 0xE7, 0xD0, 0x7F, 0x5E, 0xC7, 0x7B, 0x10, 0x71, 0x19, 0xC0, 0x4A, 0xBB, 0x2E, + 0x3F, 0xC3, 0x4D, 0xED, 0xDE, 0x18, 0x58, 0xB9, 0x20, 0x58, 0xF8, 0x26, 0xCC, 0x0B, 0xC9, 0xCA, 0x16, 0x1B, 0xF6, 0x24, 0xCF, 0x04, 0x30, 0xBC, 0x66, 0x11, 0xC8, 0xFB, 0x28, 0xC4, 0xD9, 0x4B, + 0x54, 0x25, 0x78, 0x7A, 0xDB, 0x82, 0xD9, 0x99, 0xD5, 0x36, 0xC8, 0xBF, 0xC5, 0xAE, 0xAD, 0x0F, 0xED, 0xB2, 0xDB, 0x1A, 0x84, 0x6D, 0x53, 0x4F, 0x25, 0x19, 0x73, 0x74, 0xC1, 0x0C, 0x99, 0x14, + 0xB5, 0xF4, 0x6D, 0xC8, 0x3F, 0x02, 0x26, 0x86, 0x28, 0xFC, 0x8A, 0xC1, 0x24, 0x6B, 0xD3, 0x52, 0x8B, 0x84, 0xBE, 0x0F, 0xA9, 0x41, 0x12, 0x7E, 0xBD, 0x45, 0x97, 0x0C, 0xA2, 0x15, 0x8B, 0xF7, + 0x9A, 0xA2, 0x14, 0x1B, 0x59, 0xCC, 0xE0, 0x98, 0x34, 0x17, 0x21, 0xAE, 0x4F, 0xAB, 0x6D, 0x2A, 0xAF, 0x10, 0x9F, 0x5E, 0xF6, 0xC0, 0x06, 0xB8, 0x5C, 0xCD, 0xF5, 0x0F, 0x8F, 0x79, 0xF5, 0x5B, + 0xAC, 0x2B, 0xC6, 0x8B, 0x7F, 0x9D, 0x81, 0x3A, 0xE9, 0xBE, 0xCA, 0xE6, 0x11, 0xC4, 0xC0, 0x08, 0xDC, 0xEC, 0x7D, 0xB4, 0xC2, 0xEA, 0x46, 0x37, 0x46, 0x3D, 0xC6, 0xBE, 0x33, 0xDB, 0x94, 0x40, + 0x69, 0x1D, 0x66, 0x84, 0x63, 0x6F, 0x14, 0x6A, 0x90, 0x3B, 0x18, 0x9F, 0x52, 0xB3, 0x46, 0x32, 0x29, 0x2C, 0x08, 0xE5, 0xAA, 0x28, 0xAA, 0xAB, 0x37, 0xE9, 0x12, 0x14, 0xFA, 0xFD, 0xB0, 0xDF, + 0xCF, 0x92, 0x92, 0x30, 0x2D, 0x6C, 0x97, 0xD0, 0x8E, 0x91, 0x8C, 0x7D, 0x94, 0x7B, 0x8A, 0xFD, 0xB6, 0xAB, 0xF9, 0x6B, 0xDE, 0x5B, 0x44, 0x13, 0xDC, 0xA9, 0xD2, 0x2C, 0xAD, 0xED, 0x06, 0xF8, + 0x5C, 0x1E, 0x9D, 0x7A, 0xCC, 0x12, 0xC8, 0x05, 0x53, 0xEC, 0xF5, 0x8C, 0xC6, 0xBC, 0xBB, 0x7C, 0xE3, 0xF7, 0xDB, 0x7C, 0xE9, 0xD9, 0x5B, 0x8C, 0x93, 0x77, 0xD0, 0x39, 0x3A, 0x1A, 0x5B, 0xAF, + 0x92, 0x01, 0x39, 0xCC, 0xF1, 0x1B, 0x14, 0xE9, 0xAA, 0x60, 0x3C, 0x41, 0x21, 0x54, 0xD6, 0xFA, 0x08, 0x40, 0x51, 0x08, 0x4C, 0x57, 0x85, 0x00, 0xDE, 0xCF, 0xF3, 0x1F, 0xB6, 0x1E, 0x93, 0x22, + 0xC6, 0xD6, 0x3A, 0xEE, 0x3A, 0x3A, 0xDB, 0xA7, 0x45, 0xA9, 0x1C, 0xFA, 0xC0, 0xCE, 0x21, 0x9E, 0x8C, 0x2F, 0xF9, 0x0C, 0x53, 0xE4, 0x23, 0xE2, 0x74, 0xC0, 0x41, 0xEC, 0x74, 0x12, 0xFA, 0xEE, + 0x4F, 0x4C, 0xC1, 0x11, 0x6C, 0xDC, 0x97, 0x2A, 0x90, 0xA1, 0xE0, 0x9B, 0x1F, 0x48, 0x5F, 0xDA, 0x1C, 0x17, 0xC6, 0x68, 0x2A, 0xB2, 0x6B, 0x0B, 0x23, 0x11, 0xB4, 0x53, 0x7D, 0x92, 0x39, 0x46, + 0x5B, 0x47, 0x00, 0x64, 0x25, 0xFC, 0x71, 0xB2, 0xB8, 0x55, 0x64, 0xE7, 0x37, 0xFD, 0x2B, 0x5C, 0x73, 0xAB, 0xB8, 0xFA, 0xD2, 0x0B, 0x83, 0xBF, 0x54, 0xE0, 0xBE, 0x2F, 0x6E, 0x2D, 0x71, 0xA5, + 0x16, 0x32, 0x61, 0x15, 0x31, 0x6E, 0x84, 0x5B, 0xC6, 0xCA, 0x82, 0xE1, 0x51, 0xBA, 0x4F, 0x90, 0xA7, 0x51, 0x93, 0x0E, 0x2B, 0xF3, 0x06, 0xB2, 0x5C, 0xDB, 0x38, 0xC2, 0xDA, 0x27, 0xF9, 0x1E, + 0xA1, 0xE9, 0x72, 0xB9, 0xB6, 0x61, 0x00, 0xD7, 0x52, 0x9D, 0x30, 0x2E, 0x88, 0xAF, 0x33, 0x15, 0xD6, 0xBB, 0xC8, 0x6D, 0x0E, 0x71, 0x98, 0xC1, 0x40, 0xD3, 0xFC, 0x41, 0xD5, 0x94, 0xFB, 0x5C, + 0x22, 0x02, 0x10, 0x7A, 0xC8, 0xC6, 0x5D, 0xDB, 0xCC, 0x94, 0x86, 0x14, 0xF2, 0x37, 0xA3, 0x3A, 0x87, 0x88, 0x04, 0x10, 0x41, 0xE8, 0x88, 0x8E, 0xB3, 0xEC, 0x65, 0x6F, 0x01, 0xC6, 0x95, 0x7A, + 0x87, 0x21, 0x54, 0xD3, 0x6A, 0xEF, 0x53, 0xC4, 0x39, 0xA8, 0x8F, 0x67, 0x5B, 0x5E, 0x4C, 0x12, 0x96, 0x30, 0xB2, 0x95, 0x4E, 0x7E, 0x53, 0x24, 0x72, 0x70, 0x07, 0x5D, 0x0D, 0x1E, 0xB6, 0xF0, + 0x8B, 0xEA, 0x6A, 0xA1, 0xD6, 0x13, 0x20, 0xC9, 0x83, 0x3B, 0x65, 0x37, 0xF3, 0x6D, 0x8E, 0x81, 0x99, 0xB5, 0x36, 0xA2, 0xDD, 0xDB, 0x53, 0xD8, 0x12, 0xC2, 0x21, 0x31, 0x49, 0xF2, 0x57, 0xD2, + 0x67, 0xCD, 0x6D, 0x07, 0xC0, 0xE6, 0xB1, 0x11, 0x88, 0x3B, 0xD8, 0x31, 0xB2, 0x5A, 0xAF, 0x7E, 0x39, 0xB8, 0x8B, 0x4F, 0xE9, 0x2D, 0x35, 0xE7, 0xC5, 0x3F, 0x65, 0xEE, 0xF9, 0x9C, 0xA7, 0x98, + 0x68, 0xF3, 0x50, 0x66, 0xC8, 0x8A, 0xC9, 0x6D, 0xF8, 0x3E, 0xDC, 0xC4, 0x1D, 0x90, 0x43, 0x38, 0xD8, 0xD1, 0x0D, 0x33, 0x16, 0x0F, 0xBD, 0x1B, 0xB5, 0xF6, 0xD4, 0xC6, 0xB6, 0x99, 0x85, 0x4D, + 0xDD, 0x50, 0x12, 0x89, 0x02, 0x8F, 0x68, 0xD6, 0xD1, 0xA0, 0xDB, 0x8E, 0xE6, 0x1F, 0xB1, 0x91, 0x12, 0xB3, 0x66, 0x98, 0x23, 0x82, 0x59, 0xB5, 0x2A, 0x32, 0xF4, 0x9E, 0xAD, 0x74, 0x50, 0x74, + 0xFA, 0x37, 0xF1, 0xF6, 0x8B, 0x43, 0xA3, 0x31, 0x14, 0xD7, 0xBF, 0xC6, 0x7D, 0xBD, 0xDF, 0xD4, 0x61, 0x1D, 0x41, 0xDC, 0x52, 0x49, 0x81, 0xD6, 0xFE, 0x40, 0x04, 0x01, 0x4D, 0xB9, 0x32, 0x25, + 0xA5, 0x38, 0xB5, 0xCB, 0xBA, 0x94, 0xA0, 0xFD, 0x79, 0xE9, 0x1D, 0x48, 0xBD, 0x90, 0xCC, 0x57, 0x28, 0x15, 0x20, 0xFE, 0xB6, 0x46, 0x32, 0x3C, 0x45, 0x27, 0x3B, 0xE9, 0xBD, 0xFB, 0xE9, 0xD9, + 0x9A, 0xCB, 0x70, 0x4D, 0xFB, 0x24, 0x36, 0x0F, 0x0C, 0x2E, 0xA0, 0xE8, 0x14, 0xB8, 0x05, 0x6F, 0x77, 0x61, 0xBD, 0x4D, 0x4C, 0x00, 0xC5, 0xE2, 0xBC, 0x1D, 0x1F, 0x8A, 0x4E, 0xC7, 0x79, 0x1F, + 0x6A, 0x23, 0xF2, 0xDA, 0xCB, 0x42, 0x3F, 0x29, 0xC8, 0x28, 0x02, 0xE0, 0xD1, 0xED, 0xBB, 0x6F, 0x98, 0x3B, 0x48, 0x99, 0x8B, 0xBB, 0xF4, 0xCF, 0x50, 0x5A, 0x17, 0x3D, 0x14, 0xA5, 0x85, 0xEB, + 0xFF, 0xC8, 0x97, 0x7D, 0xBE, 0xE5, 0x99, 0xEC, 0x73, 0x56, 0xE8, 0x3D, 0x65, 0xA0, 0x64, 0x53, 0xA1, 0x52, 0xF1, 0x14, 0xE6, 0x63, 0xE2, 0x73, 0x50, 0x39, 0x35, 0xAA, 0x81, 0x34, 0x2B, 0x67, + 0xC5, 0x52, 0x0B, 0x70, 0x84, 0x1B, 0xA1, 0xDF, 0x81, 0x10, 0x33, 0x0B, 0xE9, 0x21, 0x4A, 0x02, 0xCB, 0xB7, 0xAC, 0x17, 0x2F, 0x04, 0x07, 0x4F, 0x4B, 0x5C, 0x07, 0xCB, 0x8E, 0xB7, 0x2D, 0x50, + 0xAA, 0xE6, 0x3D, 0x81, 0x56, 0xFF, 0x0A, 0xF3, 0xCC, 0xD5, 0xE5, 0x14, 0x64, 0x39, 0xFE, 0xE0, 0x54, 0x11, 0x20, 0xFA, 0x15, 0xCC, 0x6B, 0xEC, 0xE6, 0xA3, 0xC2, 0xC3, 0xB0, 0x79, 0x55, 0xA7, + 0xF5, 0x4D, 0x08, 0x4C, 0x1E, 0x32, 0xA4, 0x55, 0x5E, 0x39, 0x7E, 0x44, 0x6D, 0x78, 0x99, 0x6E, 0xEB, 0xD9, 0x71, 0x15, 0xAF, 0x24, 0xEE, 0xEA, 0xCE, 0x15, 0x6B, 0x92, 0xF8, 0x66, 0xC4, 0xB1, + 0xA7, 0x2C, 0x11, 0xBE, 0x1C, 0x50, 0x77, 0x10, 0x5A, 0x19, 0x46, 0xF4, 0x79, 0xA4, 0x08, 0x46, 0x3F, 0xCF, 0x33, 0xAB, 0xDA, 0x84, 0x10, 0x94, 0xD1, 0x6D, 0xEA, 0xB9, 0x97, 0xCA, 0x6D, 0xD4, + 0x6E, 0x40, 0x94, 0x34, 0xBD, 0xE4, 0x73, 0x27, 0xA1, 0x35, 0x85, 0xB9, 0x74, 0xCF, 0xE9, 0x22, 0x8D, 0x8C, 0xBD, 0x73, 0x18, 0x5A, 0xDC, 0x02, 0xD0, 0x79, 0xCB, 0x41, 0x0F, 0x16, 0xB2, 0x32, + 0x24, 0x85, 0x48, 0x66, 0x92, 0x08, 0x8D, 0x9C, 0xCD, 0x26, 0xAC, 0x9C, 0x6F, 0x30, 0xE9, 0x36, 0xBF, 0x9C, 0xA7, 0x61, 0x59, 0x52, 0x13, 0x57, 0xA8, 0x7A, 0x5B, 0xAA, 0xB1, 0x87, 0x23, 0x7F, + 0x24, 0x05, 0x57, 0x2A, 0xD0, 0x06, 0x1A, 0xF6, 0xB6, 0xD8, 0xF8, 0xE3, 0xDD, 0x35, 0xBA, 0xB5, 0x8D, 0x92, 0xD1, 0xA1, 0xB1, 0x9A, 0xA2, 0xAB, 0xFE, 0x70, 0xEE, 0xB8, 0x49, 0xBA, 0xBE, 0x8B, + 0x64, 0x46, 0x36, 0x0A, 0xB8, 0x88, 0x5C, 0x26, 0x1D, 0xAC, 0xEB, 0xFB, 0xC4, 0xB8, 0x8C, 0x82, 0x94, 0xE6, 0xFC, 0xA1, 0x40, 0xEA, 0x7B, 0x89, 0x72, 0x36, 0x97, 0x66, 0x65, 0x00, 0xD6, 0xC7, + 0x67, 0x9D, 0x64, 0x54, 0x74, 0xC6, 0x77, 0x64, 0x2F, 0x39, 0x96, 0xB0, 0x93, 0xEB, 0xFB, 0xAD, 0xEB, 0x1E, 0x20, 0x06, 0xCA, 0x1B, 0x59, 0x3B, 0x03, 0xAC, 0x40, 0xF9, 0xC2, 0x6C, 0x6A, 0xEC, + 0xFB, 0xB9, 0xC9, 0x1A, 0xFB, 0x8B, 0x16, 0xDD, 0x49, 0x67, 0x5A, 0xC5, 0xCD, 0xEB, 0x79, 0x93, 0xC4, 0x19, 0x15, 0xB8, 0x3C, 0x64, 0x5B, 0x59, 0x60, 0xA3, 0xE7, 0x6C, 0x8E, 0x01, 0xAD, 0xE5, + 0xBA, 0xE9, 0xB7, 0xD8, 0x9E, 0x80, 0x53, 0x87, 0xF9, 0x39, 0x75, 0x86, 0x30, 0xC7, 0xC3, 0x99, 0xEC, 0xDE, 0x24, 0xF2, 0x15, 0xD1, 0x9D, 0xFE, 0xB3, 0xAC, 0xBA, 0xDB, 0x9E, 0x93, 0x00, 0x4B, + 0xCF, 0x2B, 0xE6, 0x2E, 0x4B, 0x39, 0xDF, 0xAA, 0x23, 0xCA, 0x0C, 0x4D, 0xDC, 0x17, 0x6F, 0x20, 0x29, 0xB8, 0xFE, 0x67, 0x6F, 0xAA, 0x1E, 0xCF, 0x2A, 0x0C, 0x05, 0xF1, 0x4A, 0xEF, 0x7F, 0xF2, + 0xE8, 0xC3, 0x48, 0xF3, 0xE2, 0x17, 0x91, 0xD1, 0xB5, 0x61, 0x69, 0xCF, 0x57, 0xC0, 0xFA, 0x20, 0x8A, 0xDA, 0x64, 0x2F, 0x9D, 0xCB, 0x69, 0x41, 0x2B, 0x70, 0x38, 0xAE, 0x59, 0x61, 0x5F, 0x49, + 0x57, 0x9A, 0xDF, 0x85, 0xF9, 0xD2, 0x14, 0x7A, 0x48, 0x0D, 0xEE, 0x5B, 0xD1, 0x59, 0xBB, 0x71, 0x02, 0x37, 0x83, 0x24, 0xF0, 0xAB, 0xB0, 0xEB, 0x47, 0xAF, 0x6C, 0x0C, 0xDE, 0x08, 0xD8, 0xB2, + 0x83, 0x58, 0x98, 0x05, 0x5F, 0x05, 0x3F, 0xD9, 0x93, 0x3E, 0x1D, 0x30, 0x67, 0x36, 0x45, 0xE7, 0x48, 0x8A, 0xEE, 0x87, 0x1B, 0xE3, 0x48, 0xC8, 0x51, 0xF0, 0x96, 0x9A, 0x15, 0x2B, 0xC7, 0x4D, + 0x74, 0x4B, 0x2A, 0x09, 0x9E, 0x27, 0x07, 0x0B, 0x8F, 0x56, 0x41, 0x1C, 0x81, 0x67, 0x35, 0x0B, 0x50, 0x88, 0x47, 0x55, 0xBE, 0x80, 0x61, 0xCD, 0xFF, 0x54, 0x0D, 0x35, 0x2C, 0x3D, 0x46, 0xA1, + 0x53, 0x45, 0x16, 0x8F, 0x37, 0xD4, 0x30, 0xD6, 0x86, 0x48, 0xF3, 0x27, 0xF2, 0x4B, 0x2B, 0xAD, 0xF5, 0xB4, 0x1C, 0x50, 0x10, 0xED, 0x2F, 0xC4, 0xA6, 0xC3, 0xCB, 0x72, 0x06, 0xF0, 0xDC, 0x2C, + 0xDB, 0x84, 0x35, 0xAC, 0x44, 0x1B, 0xFD, 0x57, 0x2B, 0xA2, 0x53, 0xB2, 0x82, 0xFF, 0xEC, 0xD6, 0xB6, 0xD0, 0x83, 0x67, 0x32, 0xB1, 0xFA, 0x19, 0xAD, 0xAA, 0x0D, 0xDB, 0x07, 0x00, 0x6C, 0x4F, + 0x2F, 0x6C, 0x12, 0x9B, 0xD9, 0x04, 0x1F, 0x0F, 0x38, 0xB0, 0xDC, 0x37, 0x60, 0x45, 0xAC, 0xD7, 0x96, 0x39, 0x0E, 0x52, 0xEA, 0x80, 0xDD, 0x19, 0x78, 0xC7, 0xD6, 0xD0, 0xD7, 0x9D, 0x53, 0x52, + 0xE7, 0x48, 0x4E, 0xEE, 0x97, 0xF2, 0x50, 0xF2, 0xAA, 0xB4, 0xEC, 0x14, 0x0F, 0xCB, 0xC0, 0xB2, 0x45, 0xF4, 0x11, 0x03, 0xEB, 0x39, 0xE5, 0x6C, 0x8C, 0x52, 0x62, 0x0F, 0x3F, 0x84, 0x9D, 0x29, + 0x03, 0x98, 0xB1, 0xF8, 0xBF, 0xBE, 0x4E, 0x42, 0xBB, 0x53, 0x71, 0x3C, 0x9F, 0x6E, 0x8D, 0xDA, 0x78, 0x9C, 0x53, 0x4F, 0xA2, 0x2A, 0xB3, 0xF3, 0xEC, 0x30, 0x70, 0x3D, 0x33, 0xB1, 0xDA, 0x70, + 0x94, 0x5B, 0x8A, 0x58, 0xD9, 0xAA, 0x49, 0xB1, 0x09, 0x4B, 0x5D, 0xE6, 0x33, 0x5F, 0xF4, 0xB3, 0x26, 0xDC, 0x80, 0xC1, 0x0F, 0x94, 0xA3, 0x03, 0x66, 0x68, 0xB5, 0x7F, 0xEC, 0xB4, 0xFF, 0x7D, + 0xC8, 0x53, 0xB3, 0x70, 0x10, 0xB0, 0xA2, 0x02, 0x61, 0x9E, 0x6A, 0x64, 0xDF, 0xFA, 0x17, 0x49, 0x82, 0x2D, 0x9D, 0xA5, 0x72, 0xC4, 0xC6, 0x0C, 0x3C, 0xB0, 0xAF, 0x34, 0xCC, 0x79, 0x13, 0xC5, + 0x33, 0xF7, 0x3B, 0x01, 0x82, 0xE3, 0x03, 0x0B, 0x32, 0x07, 0xFA, 0xD2, 0x9C, 0x68, 0xD8, 0xF3, 0xE4, 0x4C, 0xE6, 0xA0, 0x3D, 0xD5, 0x1C, 0x49, 0x1E, 0xD2, 0xC6, 0x90, 0x32, 0x22, 0x61, 0xBF, + 0xA8, 0xC5, 0x76, 0x88, 0xB8, 0x6A, 0xE8, 0x6E, 0xB0, 0xA2, 0x7C, 0x01, 0x7E, 0xCD, 0x67, 0xC5, 0xC0, 0x7B, 0xA3, 0x85, 0xDE, 0xDB, 0x8E, 0x5F, 0x3C, 0x80, 0x13, 0x7D, 0x2E, 0x5F, 0x29, 0xA5, + 0x99, 0xC6, 0xD2, 0x2B, 0x97, 0x07, 0x96, 0xD6, 0x01, 0x0A, 0x47, 0x27, 0xE4, 0xB3, 0xA4, 0x01, 0xD1, 0x5A, 0xA4, 0x91, 0xDF, 0x9D, 0x30, 0x21, 0xEB, 0xFC, 0xE8, 0xD2, 0xEE, 0xDA, 0x07, 0xD2, + 0xFC, 0xEF, 0x4B, 0x21, 0x48, 0x4F, 0x06, 0xB0, 0x6F, 0x4E, 0xC7, 0x9B, 0x7B, 0xFC, 0x05, 0x9E, 0xE7, 0x4E, 0x68, 0x1D, 0x01, 0x2D, 0xE3, 0xA7, 0x22, 0x85, 0x67, 0xCB, 0xA3, 0xF9, 0x7B, 0xCE, + 0x91, 0x0D, 0xB0, 0x7F, 0x7C, 0xC0, 0xBE, 0xAF, 0x59, 0x3C, 0x15, 0x3B, 0x2E, 0x2B, 0xFF, 0xA4, 0xF4, 0x21, 0x2E, 0x23, 0x48, 0x2B, 0x16, 0xE8, 0x6B, 0x14, 0xC6, 0x5C, 0xF4, 0x0A, 0xA9, 0xBE, + 0x23, 0xF3, 0xA2, 0x8E, 0x7D, 0x90, 0x83, 0xD5, 0x80, 0x41, 0x6C, 0x9B, 0xE5, 0x19, 0x73, 0xBE, 0x3D, 0x15, 0x86, 0xB7, 0x05, 0xCD, 0x1F, 0x1F, 0x9D, 0x1F, 0xF4, 0x1B, 0xEF, 0xDF, 0x1C, 0x0B, + 0x58, 0xF7, 0xFB, 0x73, 0x23, 0x50, 0x4C, 0x7E, 0xA6, 0xD0, 0xF9, 0x1F, 0xD4, 0x5B, 0x06, 0x57, 0x3B, 0x8C, 0x93, 0x02, 0x8B, 0xF7, 0xF3, 0xCC, 0xD1, 0xC8, 0xDA, 0xA6, 0x43, 0xE5, 0x97, 0xAE, + 0x21, 0x36, 0x0B, 0x97, 0x4D, 0x88, 0x9F, 0x84, 0x0E, 0x9E, 0xF7, 0x15, 0xDB, 0xD9, 0x16, 0x05, 0xE1, 0x81, 0xAE, 0x69, 0xEA, 0xBB, 0x46, 0x5F, 0xEA, 0x09, 0x55, 0xF7, 0xC6, 0x3E, 0xE3, 0x90, + 0x95, 0xC1, 0x24, 0x76, 0xE9, 0x69, 0x14, 0x41, 0xBD, 0x5B, 0xB9, 0x92, 0xC2, 0x14, 0xCA, 0x4F, 0x22, 0xBF, 0x9F, 0xC7, 0x31, 0x74, 0xD5, 0x91, 0xD0, 0xA3, 0x5D, 0x4A, 0xA4, 0x89, 0xE6, 0xCC, + 0x12, 0xEC, 0xFA, 0xBB, 0x8B, 0x21, 0xE7, 0x84, 0xB7, 0x8E, 0x97, 0x7B, 0xB8, 0x9D, 0x23, 0x80, 0x0A, 0x0F, 0x03, 0x1C, 0x5A, 0xFB, 0x23, 0x41, 0x75, 0xA5, 0xBB, 0x69, 0x8B, 0xA5, 0xD7, 0x98, + 0x55, 0x5D, 0x7E, 0xF0, 0xFF, 0xF1, 0x1E, 0x9F, 0x41, 0xE6, 0xF8, 0x2B, 0x93, 0x89, 0xFC, 0x62, 0x05, 0x03, 0xF1, 0x08, 0x1E, 0x74, 0xE0, 0xF1, 0xFD, 0xC8, 0x3D, 0x76, 0xC8, 0xDD, 0x5C, 0xFD, + 0x80, 0xD8, 0x2D, 0x29, 0x60, 0x38, 0x08, 0x4A, 0xBA, 0xA2, 0xAF, 0x68, 0xB4, 0xDE, 0xA3, 0xE7, 0x00, 0xED, 0x1A, 0x99, 0xD9, 0xEC, 0xB0, 0xFD, 0x11, 0x05, 0x26, 0x75, 0xBB, 0xDA, 0x90, 0x60, + 0x2C, 0xA9, 0xE3, 0x96, 0x69, 0x91, 0x69, 0xC6, 0x22, 0xAC, 0x52, 0x94, 0x9B, 0xFC, 0x98, 0x76, 0xEF, 0xF3, 0xFC, 0xD2, 0xD2, 0x78, 0xAE, 0xA3, 0x27, 0x9E, 0x1A, 0x01, 0x90, 0x0C, 0xA5, 0x55, + 0x0F, 0x95, 0x60, 0xD4, 0xE3, 0xD4, 0xFB, 0x5A, 0x7E, 0xF1, 0x16, 0xE0, 0xA0, 0x15, 0x68, 0x54, 0xE0, 0x05, 0xF7, 0x91, 0x35, 0x2F, 0xB6, 0x8D, 0xAC, 0x0D, 0xB0, 0x75, 0x3A, 0xA4, 0xE4, 0xB3, + 0xB0, 0x19, 0x11, 0x9E, 0x5C, 0xE2, 0xDE, 0x4E, 0x73, 0x14, 0x28, 0x7E, 0xF3, 0x84, 0xA9, 0x2C, 0x30, 0xBE, 0x01, 0x20, 0x2A, 0x6A, 0x9A, 0xDE, 0x42, 0x62, 0x4A, 0x50, 0xEE, 0x29, 0xA1, 0x8F, + 0xA2, 0x19, 0x92, 0xF1, 0x6C, 0xE0, 0x22, 0x66, 0x56, 0x9A, 0x6A, 0xE2, 0x56, 0x04, 0x1D, 0x05, 0x6A, 0xD8, 0xC7, 0x66, 0xA9, 0xA7, 0xCD, 0xF5, 0x1D, 0x90, 0x61, 0xC7, 0x46, 0x94, 0x72, 0xF2, + 0x1D, 0x6D, 0x1F, 0x0A, 0x34, 0x6E, 0xC2, 0x80, 0x02, 0x5C, 0x13, 0x87, 0x81, 0x76, 0xD7, 0xE8, 0xF4, 0x55, 0x92, 0x95, 0xBF, 0x63, 0x07, 0x94, 0x67, 0x7D, 0x18, 0x07, 0x6C, 0x55, 0x6D, 0x1C, + 0x9D, 0x51, 0x1F, 0xA6, 0xB6, 0xFC, 0x09, 0x2F, 0xC7, 0xA3, 0xEF, 0x8E, 0x0A, 0xE0, 0x2D, 0x65, 0xC9, 0x8C, 0x6D, 0xCE, 0x54, 0xFD, 0xC4, 0x52, 0x5C, 0xF0, 0xBC, 0xA4, 0xF9, 0xAA, 0x85, 0xF4, + 0xFE, 0xCC, 0x7A, 0xCD, 0x83, 0x2E, 0xAC, 0xDA, 0xFE, 0x62, 0x40, 0xE8, 0xC7, 0x88, 0xB6, 0x5D, 0xAF, 0x79, 0xAA, 0x70, 0x58, 0x3A, 0x0C, 0x34, 0x15, 0x52, 0x2E, 0x3B, 0xFE, 0xA6, 0x1A, 0x29, + 0x8D, 0xD3, 0x9E, 0x1D, 0x22, 0xCA, 0x61, 0xC5, 0x3E, 0xBF, 0x00, 0xDE, 0xC2, 0x73, 0x9B, 0x8E, 0x93, 0xAF, 0xF4, 0x21, 0x97, 0xDD, 0x43, 0x22, 0x7D, 0xEF, 0x25, 0x84, 0x64, 0x9A, 0xF7, 0xBC, + 0x7A, 0x0A, 0x60, 0xA5, 0xC4, 0xA7, 0x72, 0x18, 0xB0, 0xBE, 0x6A, 0xE5, 0xAD, 0x84, 0x19, 0x4A, 0x49, 0x01, 0xCD, 0x9F, 0x73, 0xAD, 0xB7, 0x0A, 0xF6, 0x19, 0xC3, 0x8B, 0x71, 0x62, 0x79, 0xBA, + 0x41, 0xEF, 0x99, 0xF4, 0x04, 0x40, 0xEE, 0x82, 0xEC, 0x45, 0xAC, 0xDE, 0xD3, 0x25, 0xC8, 0x36, 0xFE, 0x69, 0xB8, 0x65, 0xA5, 0xE5, 0xCD, 0x0F, 0xF8, 0x56, 0xA3, 0x0D, 0xE7, 0xF0, 0x27, 0xD8, + 0xC1, 0x3B, 0x40, 0x7D, 0x5B, 0x31, 0x62, 0x9A, 0xC1, 0xA1, 0x62, 0x08, 0xBD, 0x6A, 0xF2, 0xB7, 0xCA, 0x94, 0xB1, 0x88, 0x24, 0x9E, 0x89, 0xDA, 0x3C, 0x0F, 0xBF, 0x18, 0xA4, 0x12, 0xA8, 0x69, + 0xF5, 0xF4, 0x97, 0xAD, 0x6F, 0x72, 0xAC, 0xEE, 0xB4, 0xD0, 0x77, 0xA0, 0xB7, 0xEE, 0xDF, 0x30, 0x17, 0xD8, 0x6A, 0x79, 0x9E, 0x4A, 0x68, 0x9E, 0x43, 0x9E, 0xE5, 0x84, 0x17, 0x29, 0xE4, 0xD9, + 0x57, 0x2F, 0x8C, 0x6F, 0xE7, 0x67, 0x6E, 0xF7, 0x0A, 0x9D, 0xC0, 0x2E, 0x39, 0x37, 0xF4, 0xDF, 0xB7, 0x9B, 0x3F, 0x53, 0x52, 0x45, 0x79, 0x31, 0x18, 0x07, 0x40, 0xEA, 0xB3, 0xA3, 0x34, 0x18, + 0x23, 0x6A, 0x44, 0x29, 0x40, 0x36, 0x48, 0xA9, 0xAA, 0xD6, 0x70, 0x49, 0xE6, 0x33, 0xBD, 0x07, 0x2F, 0xFC, 0xC9, 0x71, 0xEF, 0x0F, 0xC9, 0xEE, 0x5F, 0xD2, 0xB5, 0xAE, 0xFD, 0xFE, 0xE6, 0xFC, + 0xBE, 0x0B, 0x64, 0x41, 0x80, 0x6F, 0x48, 0x55, 0x50, 0x70, 0x9B, 0x2B, 0xC4, 0xC3, 0x06, 0xAC, 0x0A, 0xD5, 0x94, 0x84, 0x91, 0xB6, 0x4C, 0xDD, 0x47, 0x32, 0x02, 0x3B, 0xE8, 0x84, 0xAB, 0xBF, + 0xBF, 0x57, 0xEA, 0xCF, 0xFF, 0x96, 0xE9, 0x35, 0x8B, 0xEE, 0x7D, 0xD6, 0x71, 0xFB, 0x15, 0xEB, 0xDF, 0x4E, 0xA6, 0x90, 0x2C, 0xB4, 0x91, 0xB5, 0x84, 0x74, 0xC3, 0x53, 0x3B, 0xA9, 0x61, 0x88, + 0xA6, 0x0B, 0x5A, 0xE3, 0xC8, 0x33, 0x81, 0xB0, 0x3A, 0x93, 0x1A, 0x65, 0xB7, 0xD7, 0x40, 0x62, 0x6D, 0xCD, 0x9F, 0xC1, 0x9C, 0x75, 0x28, 0x1C, 0x18, 0x31, 0xC9, 0x78, 0xA3, 0xA7, 0x52, 0xF0, + 0xE0, 0x0F, 0x0F, 0x90, 0xBB, 0x37, 0x0E, 0x49, 0xD4, 0xAD, 0xAE, 0xC9, 0xC6, 0x1A, 0x00, 0x8B, 0x39, 0x67, 0xC3, 0x5D, 0xE4, 0x7B, 0x27, 0x1C, 0x13, 0x4B, 0xD8, 0xFC, 0x7E, 0xF1, 0x81, 0x36, + 0xBD, 0xD4, 0x15, 0x6A, 0xA3, 0xB2, 0x50, 0x34, 0x11, 0xAD, 0x4E, 0x22, 0xE4, 0x42, 0x63, 0x1C, 0x12, 0xE1, 0x60, 0xE8, 0xDD, 0xE9, 0x2B, 0xC4, 0x97, 0xCB, 0xE2, 0x40, 0x6D, 0x6C, 0xA0, 0xC0, + 0x8F, 0x36, 0x9A, 0x04, 0x82, 0x6F, 0x27, 0x9E, 0xE2, 0x1C, 0x93, 0x7D, 0xED, 0xA2, 0xEC, 0x96, 0xF8, 0x8C, 0x34, 0x3C, 0xD4, 0xB6, 0xF9, 0x55, 0xA1, 0x4B, 0x27, 0xFF, 0x71, 0xF6, 0x91, 0xE2, + 0xBD, 0x41, 0x10, 0x13, 0x1C, 0x16, 0xDA, 0xCB, 0xB5, 0xE4, 0x25, 0xF3, 0x2A, 0xD2, 0x3C, 0x5B, 0x57, 0x7C, 0x95, 0x0F, 0xD6, 0x06, 0x1C, 0xDF, 0x64, 0x06, 0xAA, 0xAF, 0x61, 0x72, 0xA1, 0xFD, + 0xF1, 0x56, 0x29, 0x77, 0x8F, 0x7D, 0x0F, 0x8A, 0x2D, 0xF0, 0xE9, 0x79, 0x0E, 0x26, 0xD0, 0x2A, 0x4A, 0xFD, 0xB3, 0x84, 0xA1, 0xAA, 0x0B, 0x2A, 0xDC, 0x46, 0xDB, 0x6A, 0x90, 0xA3, 0xC7, 0x28, + 0x14, 0x73, 0xFA, 0x6C, 0x6A, 0x0D, 0x92, 0xA0, 0xCB, 0xDB, 0x4D, 0xCF, 0x7C, 0x36, 0x15, 0xDA, 0x68, 0xA7, 0xCD, 0x84, 0x5A, 0x7F, 0x61, 0xCF, 0xA4, 0x9D, 0x0A, 0x2E, 0x55, 0x62, 0x5C, 0xE0, + 0xE9, 0x8A, 0x6F, 0x2B, 0x0D, 0xC8, 0xED, 0xD8, 0xD2, 0xE9, 0x5B, 0x57, 0xDA, 0xCB, 0x4D, 0x6A, 0xFD, 0x17, 0xBA, 0x58, 0x32, 0x55, 0x51, 0x11, 0x50, 0x5A, 0x47, 0x4C, 0x69, 0x8E, 0xFE, 0xED, + 0x89, 0x76, 0x6D, 0x14, 0xEE, 0xFD, 0xC3, 0x56, 0xA6, 0x9F, 0xF2, 0x25, 0x58, 0x4F, 0xE3, 0xB1, 0xE2, 0x19, 0x0E, 0xF8, 0x08, 0x43, 0x07, 0x93, 0xC4, 0x8B, 0x8F, 0xEC, 0xE9, 0x02, 0x85, 0xE0, + 0x5B, 0xF3, 0x37, 0xAE, 0x0F, 0xF9, 0xF2, 0xA1, 0x91, 0x5C, 0x76, 0xB3, 0x06, 0x80, 0x95, 0xB3, 0x99, 0xFD, 0xA6, 0x2E, 0x11, 0x7D, 0x0B, 0xE9, 0xC3, 0xC8, 0xD5, 0x2C, 0xC1, 0x9D, 0x93, 0x91, + 0xA6, 0xA7, 0x5D, 0xDB, 0x8E, 0x04, 0xD1, 0xDB, 0xAE, 0x6E, 0x73, 0x05, 0x0B, 0x5B, 0x7E, 0x9F, 0x72, 0x5E, 0x08, 0x05, 0x5C, 0xCB, 0xE1, 0xD9, 0x10, 0xFD, 0x8E, 0x81, 0xBC, 0x79, 0x07, 0xF6, + 0x0B, 0xD1, 0x9F, 0x11, 0xEA, 0x79, 0x88, 0x87, 0xB3, 0xD8, 0x6A, 0x44, 0xC1, 0x57, 0x82, 0x5C, 0x81, 0xE4, 0x88, 0x38, 0xAC, 0x5D, 0x36, 0xB2, 0x5A, 0xBF, 0x6E, 0xB7, 0x2D, 0x3F, 0x32, 0x49, + 0xED, 0xED, 0xBB, 0x24, 0xD0, 0xB9, 0xEF, 0xE3, 0x4E, 0x49, 0x1F, 0x9D, 0xD8, 0xC5, 0x12, 0xC1, 0x72, 0x6F, 0x1C, 0x55, 0x61, 0x24, 0xE6, 0xF8, 0x43, 0x00, 0xD7, 0x15, 0xDB, 0xC9, 0x22, 0x90, + 0x99, 0x0D, 0x4A, 0xF4, 0x18, 0x22, 0xFE, 0xAD, 0xA6, 0x3B, 0x56, 0xA0, 0xD5, 0x0D, 0xAA, 0xB4, 0x1B, 0xFB, 0x5E, 0x21, 0xB9, 0x41, 0xD0, 0xCD, 0x33, 0x6D, 0xAC, 0xB4, 0xF5, 0x68, 0xE8, 0x2B, + 0xB0, 0x44, 0xB4, 0x75, 0xBD, 0xD5, 0x0E, 0x04, 0xD4, 0x3D, 0xC6, 0xB3, 0xA7, 0x33, 0x91, 0x50, 0x10, 0x39, 0x96, 0x42, 0x4E, 0xB7, 0xB0, 0x64, 0x89, 0x6C, 0xFE, 0x2C, 0xDB, 0x6F, 0xFE, 0xE7, + 0x30, 0x5F, 0xF5, 0x50, 0x50, 0x27, 0x94, 0xCE, 0x2C, 0x22, 0x4B, 0x6F, 0x1B, 0xD7, 0x3E, 0xD3, 0x79, 0x8B, 0xFC, 0xC0, 0xD7, 0xE5, 0x99, 0x23, 0x34, 0x17, 0x1F, 0x2D, 0xB9, 0xBC, 0x26, 0x79, + 0xA5, 0x10, 0x09, 0x19, 0x0E, 0x75, 0x12, 0xDE, 0x95, 0xE4, 0xB1, 0xAC, 0x46, 0xF0, 0x25, 0x2F, 0x0B, 0x34, 0x09, 0xE2, 0x4F, 0x24, 0x47, 0x94, 0x2E, 0x23, 0xA4, 0x2C, 0xCC, 0xC0, 0x79, 0x5C, + 0x06, 0x65, 0x1E, 0x18, 0xB3, 0x92, 0xC8, 0xB0, 0xCF, 0x07, 0x5C, 0x73, 0xB1, 0x29, 0xCC, 0x37, 0xDA, 0x9D, 0x81, 0x0A, 0xDE, 0x23, 0x7D, 0x62, 0x97, 0x19, 0xDC, 0x42, 0xAA, 0x7F, 0x33, 0x91, + 0x4E, 0x37, 0x9D, 0x30, 0x4F, 0x6A, 0xCE, 0x9F, 0xC0, 0x99, 0xEF, 0x87, 0xA0, 0x0B, 0x63, 0xC2, 0x71, 0x6D, 0x13, 0x35, 0x8D, 0xE6, 0xA6, 0x05, 0xE1, 0xF5, 0xF7, 0x0B, 0x82, 0x85, 0x53, 0x5E, + 0x7C, 0xDD, 0x3F, 0x5B, 0xBC, 0x87, 0xE1, 0x5B, 0x39, 0xB0, 0xEF, 0xAC, 0xC3, 0xB3, 0x73, 0xAD, 0x13, 0xD6, 0x9E, 0x0F, 0x56, 0xE5, 0xC1, 0x96, 0x07, 0x3E, 0x60, 0xBF, 0x9C, 0x72, 0xD7, 0x6F, + 0xD9, 0x39, 0x51, 0x1E, 0xA2, 0x27, 0x6A, 0xDC, 0x66, 0x03, 0x1B, 0xAF, 0x09, 0xF5, 0x75, 0xA5, 0x10, 0x51, 0x53, 0xAD, 0xC2, 0x55, 0x0C, 0xA3, 0x5A, 0x48, 0xDB, 0x2E, 0x2F, 0xD6, 0x9B, 0x01, + 0x3D, 0x20, 0x24, 0xDF, 0x16, 0x7A, 0xDF, 0xA1, 0x36, 0xA7, 0xDF, 0xD7, 0x3C, 0x01, 0xB4, 0x08, 0x7F, 0xEF, 0x30, 0x6F, 0x3C, 0x5B, 0xE5, 0x4A, 0x0F, 0x8A, 0xE9, 0xF1, 0xED, 0x8C, 0x71, 0x48, + 0x02, 0x09, 0x25, 0x33, 0x60, 0x6B, 0x9C, 0xA5, 0xAC, 0xBA, 0xC6, 0xE0, 0x31, 0x3F, 0xBC, 0xC7, 0xD5, 0xE2, 0xF1, 0x7E, 0xB2, 0xDC, 0x53, 0x99, 0xE6, 0xF1, 0x12, 0x19, 0x1A, 0x41, 0x7D, 0x99, + 0xA3, 0xA6, 0xAB, 0xEC, 0xF9, 0x1F, 0x33, 0xD9, 0xED, 0xFF, 0x05, 0x27, 0x93, 0xC1, 0xC6, 0xFC, 0xAF, 0xCE, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0C, 0x13, 0x16, 0x1A, 0x25, 0x2A, 0x30, 0x32, + }, + }, }; #define DILITHIUM_TV_NUM sizeof(dilithium_tv)/sizeof(struct DILITHIUM_TEST_VECTOR) diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/dsa_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/dsa_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/dsa_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/dsa_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -384,7 +384,7 @@ return rc; } -CK_RV dsa_functions() +CK_RV dsa_functions(void) { SYSTEMTIME t1, t2; CK_RV rc = CKR_OK; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/ec_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/ec_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/ec_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/ec_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -211,7 +211,7 @@ }; typedef struct signVerifyParam { - CK_MECHANISM_TYPE mechtype; + CK_MECHANISM mech; CK_ULONG inputlen; CK_ULONG parts; /* 0 means process in 1 chunk via C_Sign, * >0 means process in n chunks via @@ -219,34 +219,39 @@ */ } _signVerifyParam; +CK_IBM_ECDSA_OTHER_PARAMS other_rand = { .submechanism = CKM_IBM_ECSDSA_RAND }; +CK_IBM_ECDSA_OTHER_PARAMS other_compr_multi = + { .submechanism = CKM_IBM_ECSDSA_COMPR_MULTI }; _signVerifyParam signVerifyInput[] = { - {CKM_ECDSA, 20, 0}, - {CKM_ECDSA, 32, 0}, - {CKM_ECDSA, 48, 0}, - {CKM_ECDSA, 64, 0}, - {CKM_ECDSA_SHA1, 100, 0}, - {CKM_ECDSA_SHA1, 100, 4}, - {CKM_ECDSA_SHA1, 0, 0}, /* Empty Message via C_Sign */ - {CKM_ECDSA_SHA1, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ - {CKM_ECDSA_SHA224, 100, 0}, - {CKM_ECDSA_SHA224, 100, 4}, - {CKM_ECDSA_SHA224, 0, 0}, /* Empty Message via C_Sign */ - {CKM_ECDSA_SHA224, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ - {CKM_ECDSA_SHA256, 100, 0}, - {CKM_ECDSA_SHA256, 100, 4}, - {CKM_ECDSA_SHA256, 0, 0}, /* Empty Message via C_Sign */ - {CKM_ECDSA_SHA256, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ - {CKM_ECDSA_SHA384, 100, 0}, - {CKM_ECDSA_SHA384, 100, 4}, - {CKM_ECDSA_SHA384, 0, 0}, /* Empty Message via C_Sign */ - {CKM_ECDSA_SHA384, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ - {CKM_ECDSA_SHA512, 100, 0}, - {CKM_ECDSA_SHA512, 100, 4}, - {CKM_ECDSA_SHA512, 0, 0}, /* Empty Message via C_Sign */ - {CKM_ECDSA_SHA512, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ - {CKM_IBM_ED25519_SHA512, 100, 0}, - {CKM_IBM_ED448_SHA3, 100, 0}, + {{CKM_ECDSA, NULL, 0}, 20, 0}, + {{CKM_ECDSA, NULL, 0}, 32, 0}, + {{CKM_ECDSA, NULL, 0}, 48, 0}, + {{CKM_ECDSA, NULL, 0}, 64, 0}, + {{CKM_ECDSA_SHA1, NULL, 0}, 100, 0}, + {{CKM_ECDSA_SHA1, NULL, 0}, 100, 4}, + {{CKM_ECDSA_SHA1, NULL, 0}, 0, 0}, /* Empty Message via C_Sign */ + {{CKM_ECDSA_SHA1, NULL, 0}, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ + {{CKM_ECDSA_SHA224, NULL, 0}, 100, 0}, + {{CKM_ECDSA_SHA224, NULL, 0}, 100, 4}, + {{CKM_ECDSA_SHA224, NULL, 0}, 0, 0}, /* Empty Message via C_Sign */ + {{CKM_ECDSA_SHA224, NULL, 0}, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ + {{CKM_ECDSA_SHA256, NULL, 0}, 100, 0}, + {{CKM_ECDSA_SHA256, NULL, 0}, 100, 4}, + {{CKM_ECDSA_SHA256, NULL, 0}, 0, 0}, /* Empty Message via C_Sign */ + {{CKM_ECDSA_SHA256, NULL, 0}, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ + {{CKM_ECDSA_SHA384, NULL, 0}, 100, 0}, + {{CKM_ECDSA_SHA384, NULL, 0}, 100, 4}, + {{CKM_ECDSA_SHA384, NULL, 0}, 0, 0}, /* Empty Message via C_Sign */ + {{CKM_ECDSA_SHA384, NULL, 0}, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ + {{CKM_ECDSA_SHA512, NULL, 0}, 100, 0}, + {{CKM_ECDSA_SHA512, NULL, 0}, 100, 4}, + {{CKM_ECDSA_SHA512, NULL, 0}, 0, 0}, /* Empty Message via C_Sign */ + {{CKM_ECDSA_SHA512, NULL, 0}, 0, 1}, /* Empty Message via C_SignInit+C_SignFinal */ + {{CKM_IBM_ED25519_SHA512, NULL, 0}, 100, 0}, + {{CKM_IBM_ED448_SHA3, NULL, 0}, 100, 0}, + {{CKM_IBM_ECDSA_OTHER, &other_rand, sizeof(other_rand)}, 20, 0}, + {{CKM_IBM_ECDSA_OTHER, &other_compr_multi, sizeof(other_compr_multi)}, 20, 0}, }; #define NUM_KDFS sizeof(kdfs)/sizeof(CK_EC_KDF_TYPE) @@ -326,7 +331,7 @@ if (!mech_supported(SLOT_ID, CKM_SHA_1_HMAC)) { testcase_notice("Mechanism CKM_SHA_1_HMAC is not supported with slot " - "%ld. Skipping key check", SLOT_ID); + "%lu. Skipping key check", SLOT_ID); return CKR_OK; } if (!check_supp_keysize(SLOT_ID, CKM_SHA_1_HMAC, key_len * 8)) { @@ -356,7 +361,7 @@ * Generate EC key-pairs for parties A and B. * Derive shared secrets based on Diffie Hellman key agreement defined in PKCS#3 */ -CK_RV run_DeriveECDHKey() +CK_RV run_DeriveECDHKey(void) { CK_SESSION_HANDLE session; CK_MECHANISM mech; @@ -373,10 +378,10 @@ CK_ECDH1_DERIVE_PARAMS ecdh_parmA, ecdh_parmB; CK_BBOOL true = CK_TRUE; CK_BBOOL false = CK_FALSE; - CK_BYTE pubkeyA_value[256]; - CK_BYTE pubkeyB_value[256]; - CK_BYTE secretA_value[80000]; //enough space for lengths in secret_key_len[] - CK_BYTE deriveB_value[80000]; + CK_BYTE pubkeyA_value[256] = { 0 }; + CK_BYTE pubkeyB_value[256] = { 0 }; + CK_BYTE secretA_value[80000] = { 0 }; //enough space for lengths in secret_key_len[] + CK_BYTE deriveB_value[80000] = { 0 }; CK_OBJECT_CLASS class = CKO_SECRET_KEY; CK_KEY_TYPE key_type = CKK_GENERIC_SECRET; CK_ULONG i, j, k, m; @@ -441,6 +446,9 @@ CK_ULONG pub_attr_montgomery_len = sizeof(pub_attr_montgomery)/sizeof(CK_ATTRIBUTE); + if (is_icsf_token(SLOT_ID)) + prv_attr_len -= 1; /* ICSF does not support array attributes */ + CK_ATTRIBUTE *prv_attr_gen = prv_attr; CK_ULONG prv_attr_gen_len = prv_attr_len; CK_ATTRIBUTE *pub_attr_gen = pub_attr; @@ -651,6 +659,15 @@ continue; } + if (is_icsf_token(SLOT_ID) && secret_key_len[k] == 0) { + testcase_skip("ICSF token can not derive keys without CKA_VALUE_LEN\n"); + continue; + } + if (is_icsf_token(SLOT_ID) && secret_key_len[k] > 256) { + testcase_skip("ICSF token can not derive keys of that size\n"); + continue; + } + CK_ATTRIBUTE secretA_tmpl[] = { {CKA_VALUE, secretA_value, sizeof(secretA_value)}, }; @@ -815,8 +832,8 @@ // Compare lengths of derived secrets from key object if (secretA_tmpl[0].ulValueLen != secretB_tmpl[0].ulValueLen) { - testcase_fail("ERROR: derived key #1 length = %ld, " - "derived key #2 length = %ld", + testcase_fail("ERROR: derived key #1 length = %lu, " + "derived key #2 length = %lu", secretA_tmpl[0].ulValueLen, secretB_tmpl[0].ulValueLen); goto testcase_cleanup; @@ -882,7 +899,7 @@ /* * Run some ECDH known answer tests. */ -CK_RV run_DeriveECDHKeyKAT() +CK_RV run_DeriveECDHKeyKAT(void) { CK_SESSION_HANDLE session; CK_MECHANISM mech; @@ -900,8 +917,8 @@ CK_BBOOL false = CK_FALSE; CK_ULONG user_pin_len; CK_RV rc = CKR_OK; - CK_BYTE secretA_value[1000]; // enough space for key lengths in ecdh_tv[] - CK_BYTE secretB_value[1000]; + CK_BYTE secretA_value[1000] = { 0 }; // enough space for key lengths in ecdh_tv[] + CK_BYTE secretB_value[1000] = { 0 }; CK_ULONG i; testcase_begin("starting run_DeriveECDHKeyKAT with pkey=%X ...", pkey); @@ -976,7 +993,6 @@ rc = create_ECPrivateKey(session, ecdh_tv[i].params, ecdh_tv[i].params_len, ecdh_tv[i].privkeyA, ecdh_tv[i].privkey_len, - ecdh_tv[i].pubkeyA, ecdh_tv[i].pubkey_len, &priv_keyA, !pkey); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { @@ -1019,7 +1035,6 @@ rc = create_ECPrivateKey(session, ecdh_tv[i].params, ecdh_tv[i].params_len, ecdh_tv[i].privkeyB, ecdh_tv[i].privkey_len, - ecdh_tv[i].pubkeyB, ecdh_tv[i].pubkey_len, &priv_keyB, !pkey); if (rc != CKR_OK) { if (rc == CKR_CURVE_NOT_SUPPORTED) { @@ -1175,8 +1190,8 @@ // Compare lengths of derived secret from key object if (ecdh_tv[i].derived_key_len != secretA_tmpl[0].ulValueLen) { - testcase_fail("ERROR:derived key #1 length = %ld, " - "derived key #2 length = %ld", + testcase_fail("ERROR:derived key #1 length = %lu, " + "derived key #2 length = %lu", ecdh_tv[i].derived_key_len, secretA_tmpl[0].ulValueLen); goto testcase_cleanup; @@ -1199,8 +1214,8 @@ // Compare lengths of derived secret from key object if (ecdh_tv[i].derived_key_len != secretB_tmpl[0].ulValueLen) { - testcase_fail("ERROR:derived key #1 length = %ld, derived key #2 " - "length = %ld", ecdh_tv[i].derived_key_len, + testcase_fail("ERROR:derived key #1 length = %lu, derived key #2 " + "length = %lu", ecdh_tv[i].derived_key_len, secretB_tmpl[0].ulValueLen); goto testcase_cleanup; } @@ -1250,7 +1265,7 @@ } /* end run_DeriveECDHKeyKAT() */ CK_RV run_GenerateSignVerifyECC(CK_SESSION_HANDLE session, - CK_MECHANISM_TYPE mechType, + CK_MECHANISM *mech, CK_ULONG inputlen, CK_ULONG parts, CK_OBJECT_HANDLE priv_key, @@ -1258,27 +1273,22 @@ enum curve_type curve_type, CK_BYTE *params, CK_ULONG params_len) { - CK_MECHANISM mech2; CK_BYTE_PTR data = NULL, signature = NULL; CK_ULONG i, signaturelen; CK_MECHANISM_INFO mech_info; CK_RV rc; testcase_begin("Starting with mechtype='%s', inputlen=%lu parts=%lu, pkey=%X", - p11_get_ckm(&mechtable_funcs, mechType), inputlen, parts, pkey); - - mech2.mechanism = mechType; - mech2.ulParameterLen = 0; - mech2.pParameter = NULL; + p11_get_ckm(&mechtable_funcs, mech->mechanism), inputlen, parts, pkey); /* query the slot, check if this mech if supported */ - rc = funcs->C_GetMechanismInfo(SLOT_ID, mech2.mechanism, &mech_info); + rc = funcs->C_GetMechanismInfo(SLOT_ID, mech->mechanism, &mech_info); if (rc != CKR_OK) { if (rc == CKR_MECHANISM_INVALID) { /* no support for EC key gen? skip */ testcase_skip("Slot %u doesn't support %s", (unsigned int) SLOT_ID, - p11_get_ckm(&mechtable_funcs, mechType)); + p11_get_ckm(&mechtable_funcs, mech->mechanism)); rc = CKR_OK; goto testcase_cleanup; } else { @@ -1287,35 +1297,46 @@ } } - if ((mechType == CKM_IBM_ED25519_SHA512 || mechType == CKM_IBM_ED448_SHA3)) { + if ((mech->mechanism == CKM_IBM_ED25519_SHA512 || + mech->mechanism == CKM_IBM_ED448_SHA3)) { if (curve_type != CURVE_EDWARDS) { /* Mechanism does not match to curve type, skip */ testcase_skip("Mechanism %s can only be used with Edwards curves", - p11_get_ckm(&mechtable_funcs, mechType)); + p11_get_ckm(&mechtable_funcs, mech->mechanism)); rc = CKR_OK; goto testcase_cleanup; } - if (mechType == CKM_IBM_ED25519_SHA512 && + if (mech->mechanism == CKM_IBM_ED25519_SHA512 && memcmp(params, ed25519, MIN(params_len, sizeof(ed25519))) != 0) { /* Mechanism does not match to curve, skip */ testcase_skip("Mechanism %s can only be used with Ed25519 curve", - p11_get_ckm(&mechtable_funcs, mechType)); + p11_get_ckm(&mechtable_funcs, mech->mechanism)); rc = CKR_OK; goto testcase_cleanup; } - if (mechType == CKM_IBM_ED448_SHA3 && + if (mech->mechanism == CKM_IBM_ED448_SHA3 && memcmp(params, ed448, MIN(params_len, sizeof(ed448))) != 0) { /* Mechanism does not match to curve, skip */ testcase_skip("Mechanism %s can only be used with Ed448 curve", - p11_get_ckm(&mechtable_funcs, mechType)); + p11_get_ckm(&mechtable_funcs, mech->mechanism)); rc = CKR_OK; goto testcase_cleanup; } + } else if (mech->mechanism == CKM_IBM_ECDSA_OTHER && + memcmp(params, secp256k1, MIN(params_len, sizeof(secp256k1))) != 0 && + memcmp(params, prime256v1, MIN(params_len, sizeof(prime256v1))) != 0 && + memcmp(params, brainpoolP256r1, MIN(params_len, sizeof(brainpoolP256r1))) != 0 && + memcmp(params, brainpoolP256t1, MIN(params_len, sizeof(brainpoolP256t1)))) { + /* CKM_IBM_ECDSA_OTHER can only be used with 256-bit EC curves, skip */ + testcase_skip("Mechanism %s can only be used with 256-bit EC curves", + p11_get_ckm(&mechtable_funcs, mech->mechanism)); + rc = CKR_OK; + goto testcase_cleanup; } else { if (curve_type == CURVE_EDWARDS || curve_type == CURVE_MONTGOMERY) { /* Mechanism does not match to curve type, skip */ testcase_skip("Mechanism %s can not be used with Edwards/Montogmery curves", - p11_get_ckm(&mechtable_funcs, mechType)); + p11_get_ckm(&mechtable_funcs, mech->mechanism)); rc = CKR_OK; goto testcase_cleanup; } @@ -1335,7 +1356,7 @@ } } - rc = funcs->C_SignInit(session, &mech2, priv_key); + rc = funcs->C_SignInit(session, mech, priv_key); if (rc != CKR_OK) { testcase_error("C_SignInit rc=%s", p11_get_ckr(rc)); goto testcase_cleanup; @@ -1397,7 +1418,7 @@ } /****** Verify *******/ - rc = funcs->C_VerifyInit(session, &mech2, publ_key); + rc = funcs->C_VerifyInit(session, mech, publ_key); if (rc != CKR_OK) { testcase_error("C_VerifyInit rc=%s", p11_get_ckr(rc)); goto testcase_cleanup; @@ -1438,7 +1459,7 @@ memcpy(signature, "ABCDEFGHIJKLMNOPQRSTUV", strlen("ABCDEFGHIJKLMNOPQRSTUV")); - rc = funcs->C_VerifyInit(session, &mech2, publ_key); + rc = funcs->C_VerifyInit(session, mech, publ_key); if (rc != CKR_OK) { testcase_error("C_VerifyInit rc=%s", p11_get_ckr(rc)); goto testcase_cleanup; @@ -1463,17 +1484,27 @@ rc = funcs->C_VerifyFinal(session, signature, signaturelen); if (rc != CKR_SIGNATURE_INVALID) { - testcase_error("C_VerifyFinal rc=%s", p11_get_ckr(rc)); - PRINT_ERR(" Expected CKR_SIGNATURE_INVALID\n"); - goto testcase_cleanup; + if (rc == CKR_FUNCTION_FAILED && is_ica_token(SLOT_ID)) { + testcase_notice("C_VerifyFinal rc=%s temporarily accepted for ICA token", + p11_get_ckr(rc)); + } else { + testcase_error("C_VerifyFinal rc=%s", p11_get_ckr(rc)); + PRINT_ERR(" Expected CKR_SIGNATURE_INVALID\n"); + goto testcase_cleanup; + } } } else { rc = funcs->C_Verify(session, data != NULL ? data : (CK_BYTE *)"", inputlen, signature, signaturelen); if (rc != CKR_SIGNATURE_INVALID) { - testcase_error("C_Verify rc=%s", p11_get_ckr(rc)); - PRINT_ERR(" Expected CKR_SIGNATURE_INVALID\n"); - goto testcase_cleanup; + if (rc == CKR_FUNCTION_FAILED && is_ica_token(SLOT_ID)) { + testcase_notice("C_Verify rc=%s temporarily accepted for ICA token", + p11_get_ckr(rc)); + } else { + testcase_error("C_Verify rc=%s", p11_get_ckr(rc)); + PRINT_ERR(" Expected CKR_SIGNATURE_INVALID\n"); + goto testcase_cleanup; + } } } @@ -1488,7 +1519,7 @@ return rc; } -CK_RV run_GenerateECCKeyPairSignVerify() +CK_RV run_GenerateECCKeyPairSignVerify(void) { CK_MECHANISM mech; CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; @@ -1595,7 +1626,7 @@ j < (sizeof(signVerifyInput) / sizeof(_signVerifyParam)); j++) { testcase_new_assertion(); rc = run_GenerateSignVerifyECC(session, - signVerifyInput[j].mechtype, + &signVerifyInput[j].mech, signVerifyInput[j].inputlen, signVerifyInput[j].parts, priv_key, publ_key, @@ -1642,7 +1673,7 @@ return rc; } -CK_RV run_ImportECCKeyPairSignVerify() +CK_RV run_ImportECCKeyPairSignVerify(void) { CK_MECHANISM mech; CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; @@ -1684,7 +1715,8 @@ } for (i = 0; i < EC_TV_NUM; i++) { - if ((is_ica_token(SLOT_ID) || is_cca_token(SLOT_ID))) { + if ((is_ica_token(SLOT_ID) || is_cca_token(SLOT_ID) || + is_icsf_token(SLOT_ID))) { if (!curve_supported((char *)ec_tv[i].name)) { testcase_skip("Slot %u doesn't support this curve: %s", (unsigned int)SLOT_ID,ec_tv[i].name); @@ -1694,7 +1726,6 @@ rc = create_ECPrivateKey(session, ec_tv[i].params, ec_tv[i].params_len, ec_tv[i].privkey, ec_tv[i].privkey_len, - ec_tv[i].pubkey, ec_tv[i].pubkey_len, &priv_key, !pkey); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { @@ -1765,7 +1796,7 @@ j < (sizeof(signVerifyInput) / sizeof(_signVerifyParam)); j++) { testcase_new_assertion(); rc = run_GenerateSignVerifyECC(session, - signVerifyInput[j].mechtype, + &signVerifyInput[j].mech, signVerifyInput[j].inputlen, signVerifyInput[j].parts, priv_key, publ_key, @@ -1806,7 +1837,7 @@ return rc; } -CK_RV run_TransferECCKeyPairSignVerify() +CK_RV run_TransferECCKeyPairSignVerify(void) { CK_MECHANISM mech; CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; @@ -1903,7 +1934,6 @@ rc = create_ECPrivateKey(session, ec_tv[i].params, ec_tv[i].params_len, ec_tv[i].privkey, ec_tv[i].privkey_len, - ec_tv[i].pubkey, ec_tv[i].pubkey_len, &priv_key, CK_TRUE); // key to be wrapped must be extractable if (rc != CKR_OK) { @@ -2007,15 +2037,18 @@ {CKA_WRAP_TEMPLATE, &cka_wrap_tmpl, sizeof(cka_wrap_tmpl)}, {CKA_UNWRAP_TEMPLATE, &cka_unwrap_tmpl, sizeof(cka_unwrap_tmpl)}, }; + CK_ULONG secret_tmpl_len = sizeof(secret_tmpl) / sizeof(CK_ATTRIBUTE); if (ec_tv[i].curve_type == CURVE_EDWARDS) derive = FALSE; if (ec_tv[i].curve_type == CURVE_MONTGOMERY) sign = FALSE; + if (is_icsf_token(SLOT_ID)) + secret_tmpl_len -= 2; /* ICSF does not support array-attributes */ + rc = funcs->C_GenerateKey(session, &aes_keygen_mech, secret_tmpl, - sizeof(secret_tmpl) / sizeof(CK_ATTRIBUTE), - &secret_key); + secret_tmpl_len, &secret_key); if (rc != CKR_OK) { testcase_error("C_GenerateKey, rc=%s", p11_get_ckr(rc)); goto testcase_cleanup; @@ -2054,7 +2087,6 @@ CK_OBJECT_CLASS class = CKO_PRIVATE_KEY; CK_KEY_TYPE key_type = CKK_EC; CK_BYTE unwrap_label[] = "unwrapped_private_EC_Key"; - CK_BYTE subject[] = {0}; CK_BYTE id[] = { 123 }; CK_ATTRIBUTE unwrap_tmpl[] = { @@ -2062,19 +2094,21 @@ {CKA_KEY_TYPE, &key_type, sizeof(key_type)}, {CKA_TOKEN, &true, sizeof(true)}, {CKA_LABEL, &unwrap_label, sizeof(unwrap_label)}, - {CKA_SUBJECT, subject, sizeof(subject)}, {CKA_ID, id, sizeof(id)}, {CKA_SENSITIVE, &true, sizeof(true)}, {CKA_DERIVE, &derive, sizeof(derive)}, {CKA_SIGN, &sign, sizeof(sign)}, - {CKA_IBM_PROTKEY_EXTRACTABLE, &true, sizeof(true)}, {CKA_EXTRACTABLE, &false, sizeof(false)}, + {CKA_IBM_PROTKEY_EXTRACTABLE, &true, sizeof(true)}, }; + CK_ULONG unwrap_tmpl_len = sizeof(unwrap_tmpl) / sizeof(CK_ATTRIBUTE); + + if (is_icsf_token(SLOT_ID)) + unwrap_tmpl_len -= 1; /* ICSF does not supp. CKA_IBM_PROTKEY_... */ rc = funcs->C_UnwrapKey(session, &wrap_mech, secret_key, wrapped_key, wrapped_keylen, - unwrap_tmpl, - sizeof(unwrap_tmpl) / sizeof(CK_ATTRIBUTE), + unwrap_tmpl, unwrap_tmpl_len, &unwrapped_key); if (rc != CKR_OK) { testcase_fail("C_UnwrapKey, rc=%s", p11_get_ckr(rc)); @@ -2092,7 +2126,7 @@ j < (sizeof(signVerifyInput) / sizeof(_signVerifyParam)); j++) { testcase_new_assertion(); rc = run_GenerateSignVerifyECC(session, - signVerifyInput[j].mechtype, + &signVerifyInput[j].mech, signVerifyInput[j].inputlen, signVerifyInput[j].parts, unwrapped_key, publ_key, @@ -2158,7 +2192,7 @@ * card. So the actual behavior of this testcase heavily depends on the * machine and token config. */ -CK_RV run_ImportSignVerify_Pkey() +CK_RV run_ImportSignVerify_Pkey(void) { CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; CK_SESSION_HANDLE session; @@ -2347,6 +2381,363 @@ return rc; } +struct btc_test { + const _ec_struct ec; + CK_ULONG master_key_derive; + CK_ULONG priv_to_pub; + CK_ULONG priv_to_priv; + CK_ULONG pub_to_pub; +}; + +static const struct btc_test btc_tests[] = { + { .ec = { &secp256k1, sizeof(secp256k1), CK_FALSE, CURVE_PRIME, + CURVE256_LENGTH, "secp256k1" }, + .master_key_derive = CK_IBM_BTC_BIP0032_MASTERK, + .priv_to_pub = CK_IBM_BTC_BIP0032_PRV2PUB, + .priv_to_priv = CK_IBM_BTC_BIP0032_PRV2PRV, + .pub_to_pub = CK_IBM_BTC_BIP0032_PUB2PUB, + }, + { .ec = { &secp256k1, sizeof(secp256k1), CK_FALSE, CURVE_PRIME, + CURVE256_LENGTH, "secp256k1" }, + .master_key_derive = CK_IBM_BTC_SLIP0010_MASTERK, + .priv_to_pub = CK_IBM_BTC_SLIP0010_PRV2PUB, + .priv_to_priv = CK_IBM_BTC_SLIP0010_PRV2PRV, + .pub_to_pub = CK_IBM_BTC_SLIP0010_PUB2PUB, + }, + { .ec = { &prime256v1, sizeof(prime256v1), CK_FALSE, CURVE_PRIME, + CURVE256_LENGTH, "prime256v1" }, + .master_key_derive = CK_IBM_BTC_SLIP0010_MASTERK, + .priv_to_pub = CK_IBM_BTC_SLIP0010_PRV2PUB, + .priv_to_priv = CK_IBM_BTC_SLIP0010_PRV2PRV, + .pub_to_pub = CK_IBM_BTC_SLIP0010_PUB2PUB, + }, + { .ec = { &ed25519, sizeof(ed25519), CK_FALSE, CURVE_EDWARDS, + CURVE256_LENGTH, "ed25519" }, + .master_key_derive = CK_IBM_BTC_SLIP0010_MASTERK, + .priv_to_pub = CK_IBM_BTC_SLIP0010_PRV2PUB, + .priv_to_priv = CK_IBM_BTC_SLIP0010_PRV2PRV, + .pub_to_pub = CK_IBM_BTC_SLIP0010_PUB2PUB, + }, +}; + +#define NUM_BTC_TESTS 4 + +static const CK_ULONG btc_child_key_index[] = { + 0, + 0x12, + 0x3456, + 0x987654, + 0x7fffffff, + 0 + CK_IBM_BTC_BIP0032_HARDENED, + 0x12 + CK_IBM_BTC_BIP0032_HARDENED, + 0x3456 + CK_IBM_BTC_BIP0032_HARDENED, + 0x987654 + CK_IBM_BTC_BIP0032_HARDENED, + 0x7fffffff + CK_IBM_BTC_BIP0032_HARDENED, +}; + +#define NUM_BTC_CHILD_KEY_INDEXES 10 + +static const char *btc_type_to_str(CK_ULONG btc_type) +{ + switch (btc_type) { + case CK_IBM_BTC_BIP0032_PRV2PRV: + return "CK_IBM_BTC_BIP0032_PRV2PRV"; + case CK_IBM_BTC_BIP0032_PRV2PUB: + return "CK_IBM_BTC_BIP0032_PRV2PUB"; + case CK_IBM_BTC_BIP0032_PUB2PUB: + return "CK_IBM_BTC_BIP0032_PUB2PUB"; + case CK_IBM_BTC_BIP0032_MASTERK: + return "CK_IBM_BTC_BIP0032_MASTERK"; + case CK_IBM_BTC_SLIP0010_PRV2PRV: + return "CK_IBM_BTC_SLIP0010_PRV2PRV"; + case CK_IBM_BTC_SLIP0010_PRV2PUB: + return "CK_IBM_BTC_SLIP0010_PRV2PUB"; + case CK_IBM_BTC_SLIP0010_PUB2PUB: + return "CK_IBM_BTC_SLIP0010_PUB2PUB"; + case CK_IBM_BTC_SLIP0010_MASTERK: + return "CK_IBM_BTC_SLIP0010_MASTERK"; + default: + return "UNKNOWN"; + } +} + +/* + * Run Bitcoin Key Derivation tests: + * Derive a BTC master key from a generic secret key. Then derive a number of + * child keys (public and private, hardened and non hardened) from the master + * key. + */ +CK_RV run_DeriveBTC(void) +{ + CK_SESSION_HANDLE session; + CK_MECHANISM mech; + CK_FLAGS flags; + CK_OBJECT_HANDLE secret = CK_INVALID_HANDLE, master = CK_INVALID_HANDLE; + CK_OBJECT_HANDLE child_priv = CK_INVALID_HANDLE, child_pub = CK_INVALID_HANDLE; + CK_OBJECT_HANDLE child_pub2 = CK_INVALID_HANDLE; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len; + CK_RV rc = CKR_OK; + CK_BBOOL true = CK_TRUE; + CK_IBM_BTC_DERIVE_PARAMS btc_parms; + CK_BYTE master_chain_code[CK_IBM_BTC_CHAINCODE_LENGTH]; + CK_BYTE child_chain_code[CK_IBM_BTC_CHAINCODE_LENGTH]; + CK_OBJECT_CLASS priv_class = CKO_PRIVATE_KEY; + CK_OBJECT_CLASS pub_class = CKO_PUBLIC_KEY; + CK_KEY_TYPE key_type = CKK_EC; + CK_OBJECT_CLASS secret_class = CKO_SECRET_KEY; + CK_ULONG secret_keylen = 32; + CK_ULONG i, k; + + testsuite_begin("starting run_DeriveBTC with pkey=%X ...", pkey); + testcase_rw_session(); + testcase_user_login(); + + /* Skip tests if pkey = true, but the slot doesn't support protected keys*/ + if (pkey && !is_ep11_token(SLOT_ID)) { + testcase_skip("pkey test option is true, but slot %u doesn't support protected keys", + (unsigned int) SLOT_ID); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, CKM_GENERIC_SECRET_KEY_GEN)) { + testcase_skip("Slot %u doesn't support CKM_GENERIC_SECRET_KEY_GEN\n", + (unsigned int) SLOT_ID); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, CKM_IBM_BTC_DERIVE)) { + testcase_skip("Slot %u doesn't support CKM_IBM_BTC_DERIVE\n", + (unsigned int) SLOT_ID); + goto testcase_cleanup; + } + + for (i = 0; i < NUM_BTC_TESTS; i++) { + CK_ATTRIBUTE secret_tmpl[] = { + {CKA_CLASS, &secret_class, sizeof(secret_class)}, + {CKA_VALUE_LEN, &secret_keylen, sizeof(secret_keylen)}, + {CKA_IBM_USE_AS_DATA, &true, sizeof(true)}, + }; + CK_ULONG secret_tmpl_len = sizeof(secret_tmpl) / sizeof(CK_ATTRIBUTE); + CK_ATTRIBUTE priv_derive_tmpl[] = { + {CKA_CLASS, &priv_class, sizeof(priv_class)}, + {CKA_KEY_TYPE, &key_type, sizeof(key_type)}, + {CKA_DERIVE, &true, sizeof(true)}, + {CKA_EC_PARAMS, (CK_VOID_PTR)btc_tests[i].ec.curve, btc_tests[i].ec.size}, + {CKA_IBM_USE_AS_DATA, &true, sizeof(true)}, + }; + CK_ULONG priv_derive_tmpl_len = sizeof(priv_derive_tmpl) / sizeof(CK_ATTRIBUTE); + CK_ATTRIBUTE pub_derive_tmpl[] = { + {CKA_CLASS, &pub_class, sizeof(pub_class)}, + {CKA_KEY_TYPE, &key_type, sizeof(key_type)}, + {CKA_DERIVE, &true, sizeof(true)}, + {CKA_EC_PARAMS, (CK_VOID_PTR)btc_tests[i].ec.curve, btc_tests[i].ec.size}, + {CKA_IBM_USE_AS_DATA, &true, sizeof(true)}, + }; + CK_ULONG pub_derive_tmpl_len = sizeof(pub_derive_tmpl) / sizeof(CK_ATTRIBUTE); + + /* Testcase #1: Derive the BTC master key from a secret key */ + testcase_new_assertion(); + testcase_begin("BTC master key derive with curve=%s and type=%s, pkey=%X", + btc_tests[i].ec.name, + btc_type_to_str(btc_tests[i].master_key_derive), pkey); + + mech.mechanism = CKM_GENERIC_SECRET_KEY_GEN; + mech.ulParameterLen = 0; + mech.pParameter = NULL; + + rc = funcs->C_GenerateKey(session, &mech, secret_tmpl, secret_tmpl_len, + &secret); + if (rc != CKR_OK) { + testcase_fail("C_GenerateKey, rc=%s", p11_get_ckr(rc)); + goto run_cleanup; + } + + mech.mechanism = CKM_IBM_BTC_DERIVE; + mech.ulParameterLen = sizeof(CK_IBM_BTC_DERIVE_PARAMS); + mech.pParameter = &btc_parms; + + memset(master_chain_code, 0, sizeof(master_chain_code)); + memset(&btc_parms, 0, sizeof(btc_parms)); + btc_parms.version = CK_IBM_BTC_DERIVE_PARAMS_VERSION_1; + btc_parms.type = btc_tests[i].master_key_derive; + btc_parms.childKeyIndex = 0; + btc_parms.ulChainCodeLen = 0; + btc_parms.pChainCode = master_chain_code; + + rc = funcs->C_DeriveKey(session, &mech, + secret, priv_derive_tmpl, + priv_derive_tmpl_len, &master); + if (rc != CKR_OK) { + testcase_fail("C_DeriveKey BTC master key: rc = %s", + p11_get_ckr(rc)); + goto run_cleanup; + } + + testcase_pass("BTC master key derive with curve=%s and type=%s, pkey=%X", + btc_tests[i].ec.name, + btc_type_to_str(btc_tests[i].master_key_derive), pkey); + + /* Derive child keys from the master key */ + for (k = 0; k < NUM_BTC_CHILD_KEY_INDEXES; k++) { + /* Testcase #2: Derive private child key from private master key */ + + /* For ed25519 only hardened child keys are supported (SLIP0010) */ + if (btc_tests[i].master_key_derive == CK_IBM_BTC_SLIP0010_MASTERK && + btc_tests[i].ec.type == CURVE_EDWARDS && + (btc_child_key_index[k] & CK_IBM_BTC_BIP0032_HARDENED) == 0) + continue; + + testcase_new_assertion(); + testcase_begin("BTC priv-to-priv child key derive with curve=%s child-key-index=0x%lx and type=%s, pkey=%X", + btc_tests[i].ec.name, btc_child_key_index[k], + btc_type_to_str(btc_tests[i].priv_to_priv), pkey); + + mech.mechanism = CKM_IBM_BTC_DERIVE; + mech.ulParameterLen = sizeof(CK_IBM_BTC_DERIVE_PARAMS); + mech.pParameter = &btc_parms; + + memcpy(child_chain_code, master_chain_code, sizeof(master_chain_code)); + memset(&btc_parms, 0, sizeof(btc_parms)); + btc_parms.version = CK_IBM_BTC_DERIVE_PARAMS_VERSION_1; + btc_parms.type = btc_tests[i].priv_to_priv; + btc_parms.childKeyIndex = btc_child_key_index[k]; + btc_parms.ulChainCodeLen = sizeof(child_chain_code); + btc_parms.pChainCode = child_chain_code; + + rc = funcs->C_DeriveKey(session, &mech, + master, priv_derive_tmpl, + priv_derive_tmpl_len, &child_priv); + if (rc != CKR_OK) { + testcase_fail("C_DeriveKey BTC child key (priv): rc = %s", + p11_get_ckr(rc)); + goto run_child_cleanup; + } + + testcase_pass("BTC priv-to-priv child key derive with curve=%s child-key-index=0x%lx and type=%s, pkey=%X", + btc_tests[i].ec.name, btc_child_key_index[k], + btc_type_to_str(btc_tests[i].priv_to_priv), pkey); + + /* Testcase #3: Derive public child key from private master key */ + testcase_new_assertion(); + testcase_begin("BTC priv-to-pub child key derive with curve=%s child-key-index=0x%lx and type=%s, pkey=%X", + btc_tests[i].ec.name, btc_child_key_index[k], + btc_type_to_str(btc_tests[i].priv_to_pub), pkey); + + mech.mechanism = CKM_IBM_BTC_DERIVE; + mech.ulParameterLen = sizeof(CK_IBM_BTC_DERIVE_PARAMS); + mech.pParameter = &btc_parms; + + memcpy(child_chain_code, master_chain_code, sizeof(master_chain_code)); + memset(&btc_parms, 0, sizeof(btc_parms)); + btc_parms.version = CK_IBM_BTC_DERIVE_PARAMS_VERSION_1; + btc_parms.type = btc_tests[i].priv_to_pub; + btc_parms.childKeyIndex = btc_child_key_index[k]; + btc_parms.ulChainCodeLen = sizeof(child_chain_code); + btc_parms.pChainCode = child_chain_code; + + rc = funcs->C_DeriveKey(session, &mech, + master, pub_derive_tmpl, + pub_derive_tmpl_len, &child_pub); + if (rc != CKR_OK) { + testcase_fail("C_DeriveKey BTC child key (pub): rc = %s", + p11_get_ckr(rc)); + goto run_child_cleanup; + } + + testcase_pass("BTC priv-to-pub child key derive with curve=%s child-key-index=0x%lx and type=%s, pkey=%X", + btc_tests[i].ec.name, btc_child_key_index[k], + btc_type_to_str(btc_tests[i].priv_to_pub), pkey); + + /* Testcase #4: Test if derived keys are usable */ + testcase_new_assertion(); + + if (btc_tests[i].ec.type == CURVE_EDWARDS) + mech.mechanism = CKM_IBM_ED25519_SHA512; + else + mech.mechanism = CKM_ECDSA; + mech.ulParameterLen = 0; + mech.pParameter = NULL; + + rc = run_GenerateSignVerifyECC(session, &mech, 20, 0, + child_priv, child_pub, + btc_tests[i].ec.type, + (CK_BYTE *)btc_tests[i].ec.curve, + btc_tests[i].ec.size); + if (rc != 0) { + testcase_fail("run_GenerateSignVerifyECC failed."); + goto testcase_cleanup; + } + testcase_pass("BTC check derived keys with curve=%s child-key-index=0x%lx, pkey=%X", + btc_tests[i].ec.name, btc_child_key_index[k], pkey); + + /* + * Testcase #5: Derive public child key from public key + * (non-hardened keys only, thus not supported for ed25519) + */ + if ((btc_child_key_index[k] & CK_IBM_BTC_BIP0032_HARDENED) != 0) + goto run_child_cleanup; + + testcase_new_assertion(); + testcase_begin("BTC pub-to-pub child key derive with curve=%s child-key-index=0x%lx and type=%s, pkey=%X", + btc_tests[i].ec.name, btc_child_key_index[k], + btc_type_to_str(btc_tests[i].pub_to_pub), pkey); + + mech.mechanism = CKM_IBM_BTC_DERIVE; + mech.ulParameterLen = sizeof(CK_IBM_BTC_DERIVE_PARAMS); + mech.pParameter = &btc_parms; + + memset(&btc_parms, 0, sizeof(btc_parms)); + btc_parms.version = CK_IBM_BTC_DERIVE_PARAMS_VERSION_1; + btc_parms.type = btc_tests[i].pub_to_pub; + btc_parms.childKeyIndex = btc_child_key_index[k]; + btc_parms.ulChainCodeLen = sizeof(child_chain_code); + btc_parms.pChainCode = child_chain_code; + + rc = funcs->C_DeriveKey(session, &mech, + child_pub, pub_derive_tmpl, + pub_derive_tmpl_len, &child_pub2); + if (rc != CKR_OK) { + testcase_fail("C_DeriveKey BTC child key (pub): rc = %s", + p11_get_ckr(rc)); + goto run_child_cleanup; + } + + testcase_pass("BTC pub-to-pub child key derive with curve=%s child-key-index=0x%lx and type=%s, pkey=%X", + btc_tests[i].ec.name, btc_child_key_index[k], + btc_type_to_str(btc_tests[i].pub_to_pub), pkey); + +run_child_cleanup: + if (child_priv != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, child_priv); + child_priv = CK_INVALID_HANDLE; + if (child_pub != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, child_pub); + child_pub = CK_INVALID_HANDLE; + if (child_pub2 != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, child_pub2); + child_pub2 = CK_INVALID_HANDLE; + } + +run_cleanup: + if (secret != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, secret); + secret = CK_INVALID_HANDLE; + if (master != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, master); + master = CK_INVALID_HANDLE; + } + +testcase_cleanup: + if (secret != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, secret); + if (master != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, master); + + testcase_user_logout(); + testcase_close_session(); + + return rc; +} /* end run_DeriveBTC() */ + int main(int argc, char **argv) { CK_C_INITIALIZE_ARGS cinit_args; @@ -2393,6 +2784,7 @@ rv += run_TransferECCKeyPairSignVerify(); rv += run_DeriveECDHKey(); rv += run_DeriveECDHKeyKAT(); + rv += run_DeriveBTC(); if (is_ep11_token(SLOT_ID)) { pkey = CK_TRUE; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/kyber_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/kyber_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/kyber_func.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/kyber_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,1174 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#include + +#include +#include +#include +#include + +#include "pkcs11types.h" +#include "regress.h" +#include "common.c" +#include "defs.h" +#include "kyber.h" +#include "mechtable.h" +#include "pqc_oids.h" +#include "ec_curves.h" + +/** + * Experimental Support for Kyber keys and KEM + * with oid = 1.3.6.1.4.1.2.267.5.xxx + */ + +const CK_BYTE kyber_r2_768[] = OCK_KYBER_R2_768; +const CK_BYTE kyber_r2_1024[] = OCK_KYBER_R2_1024; + +const CK_BYTE prime256v1[] = OCK_PRIME256V1; + +typedef struct variant_info { + const char *name; + CK_ULONG keyform; + const CK_BYTE *oid; + CK_ULONG oid_len; +} _variant_info; + +const _variant_info variants[] = { + { "DEFAULT (KYBER_R2_1024)", 0, NULL, 0 }, + { "KYBER_R2_768", CK_IBM_KYBER_KEYFORM_ROUND2_768, + kyber_r2_768, sizeof(kyber_r2_768) }, + { "KYBER_R2_1024", CK_IBM_KYBER_KEYFORM_ROUND2_1024, + kyber_r2_1024, sizeof(kyber_r2_1024) }, +}; + +const CK_ULONG num_variants = sizeof(variants) / sizeof(_variant_info); + +typedef struct kemParam { + CK_IBM_KYBER_KDF_TYPE kdf; + CK_ULONG secret_key_len; + CK_ULONG shard_data_len; + CK_BYTE shared_data[32]; + CK_BBOOL hybrid; +} _kemParam; + +const _kemParam kemInput[] = { + { CKD_NULL, 32, 0, {0x00}, CK_FALSE }, + { CKD_IBM_HYBRID_SHA1_KDF, 16, 0, {0x00}, CK_TRUE }, + { CKD_IBM_HYBRID_SHA1_KDF, 32, 16, + { 0x32,0x3F,0xA3,0x16,0x9D,0x8E,0x9C,0x65,0x93,0xF5,0x94,0x76,0xBC,0x14,0x20,0x00 }, + CK_TRUE }, + { CKD_IBM_HYBRID_SHA224_KDF, 16, 0, {0x00}, CK_TRUE }, + { CKD_IBM_HYBRID_SHA224_KDF, 32, 16, + { 0x32,0x3F,0xA3,0x16,0x9D,0x8E,0x9C,0x65,0x93,0xF5,0x94,0x76,0xBC,0x14,0x20,0x00 }, + CK_TRUE }, + { CKD_IBM_HYBRID_SHA256_KDF, 16, 0, {0x00}, CK_TRUE }, + { CKD_IBM_HYBRID_SHA256_KDF, 32, 16, + { 0x32,0x3F,0xA3,0x16,0x9D,0x8E,0x9C,0x65,0x93,0xF5,0x94,0x76,0xBC,0x14,0x20,0x00 }, + CK_TRUE }, + { CKD_IBM_HYBRID_SHA384_KDF, 16, 0, {0x00}, CK_TRUE }, + { CKD_IBM_HYBRID_SHA384_KDF, 32, 16, + { 0x32,0x3F,0xA3,0x16,0x9D,0x8E,0x9C,0x65,0x93,0xF5,0x94,0x76,0xBC,0x14,0x20,0x00 }, + CK_TRUE }, + { CKD_IBM_HYBRID_SHA512_KDF, 16, 0, {0x00}, CK_TRUE }, + { CKD_IBM_HYBRID_SHA512_KDF, 32, 16, + { 0x32,0x3F,0xA3,0x16,0x9D,0x8E,0x9C,0x65,0x93,0xF5,0x94,0x76,0xBC,0x14,0x20,0x00 }, + CK_TRUE }, +}; + +static const char *p11_get_ckd(CK_EC_KDF_TYPE kdf) +{ + switch (kdf) { + case CKD_NULL: + return "CKD_NULL"; + case CKD_SHA1_KDF: + return "CKD_SHA1_KDF"; + case CKD_SHA224_KDF: + return "CKD_SHA224_KDF"; + case CKD_SHA256_KDF: + return "CKD_SHA256_KDF"; + case CKD_SHA384_KDF: + return "CKD_SHA384_KDF"; + case CKD_SHA512_KDF: + return "CKD_SHA512_KDF"; + case CKD_IBM_HYBRID_NULL: + return "CKD_IBM_HYBRID_NULL"; + case CKD_IBM_HYBRID_SHA1_KDF: + return "CKD_IBM_HYBRID_SHA1_KDF"; + case CKD_IBM_HYBRID_SHA224_KDF: + return "CKD_IBM_HYBRID_SHA224_KDF"; + case CKD_IBM_HYBRID_SHA256_KDF: + return "CKD_IBM_HYBRID_SHA256_KDF"; + case CKD_IBM_HYBRID_SHA384_KDF: + return "CKD_IBM_HYBRID_SHA384_KDF"; + case CKD_IBM_HYBRID_SHA512_KDF: + return "CKD_IBM_HYBRID_SHA512_KDF"; + default: + return "UNKNOWN"; + } +} + +#define NUM_KEM_INPUTS sizeof(kemInput)/sizeof(_kemParam) + +/* + * Perform a HMAC sign to verify that the key is usable. + */ +CK_RV run_HMACSign(CK_SESSION_HANDLE session, CK_OBJECT_HANDLE h_key1, + CK_OBJECT_HANDLE h_key2, CK_ULONG key_len) +{ + CK_MECHANISM mech = { .mechanism = CKM_SHA_1_HMAC, + .pParameter = NULL, .ulParameterLen = 0 }; + CK_BYTE data[32] = { 0 }; + CK_BYTE mac[SHA1_HASH_SIZE] = { 0 }; + CK_ULONG mac_len = sizeof(mac); + CK_RV rc = CKR_OK; + + if (!mech_supported(SLOT_ID, CKM_SHA_1_HMAC)) { + testcase_notice("Mechanism CKM_SHA_1_HMAC is not supported with slot " + "%lu. Skipping key check", SLOT_ID); + return CKR_OK; + } + if (!check_supp_keysize(SLOT_ID, CKM_SHA_1_HMAC, key_len * 8)) { + testcase_notice("Mechanism CKM_SHA_1_HMAC can not be used with keys " + "of size %lu. Skipping key check", key_len); + return CKR_OK; + } + + rc = funcs->C_SignInit(session, &mech, h_key1); + if (rc != CKR_OK) { + testcase_notice("C_SignInit rc=%s", p11_get_ckr(rc)); + goto error; + } + + /** do signing **/ + rc = funcs->C_Sign(session, data, sizeof(data), mac, &mac_len); + if (rc != CKR_OK) { + testcase_notice("C_Sign rc=%s", p11_get_ckr(rc)); + goto error; + } + + rc = funcs->C_VerifyInit(session, &mech, h_key2); + if (rc != CKR_OK) { + testcase_notice("C_VerifyInit rc=%s", p11_get_ckr(rc)); + goto error; + } + + /** do verify **/ + rc = funcs->C_Verify(session, data, sizeof(data), mac, mac_len); + if (rc != CKR_OK) { + testcase_notice("C_Verify rc=%s", p11_get_ckr(rc)); + goto error; + } + +error: + return rc; +} + +CK_RV ecdh_derive_secret(CK_SESSION_HANDLE session, CK_ULONG secret_key_len, + CK_EC_KDF_TYPE kdf, CK_OBJECT_HANDLE *hybrid_key) +{ + CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE; + CK_OBJECT_HANDLE priv_key = CK_INVALID_HANDLE; + CK_ECDH1_DERIVE_PARAMS ecda_params; + CK_MECHANISM mech; + CK_RV rc; + + CK_BYTE pubkey_value[256]; + CK_ATTRIBUTE extr_tmpl[] = { + {CKA_EC_POINT, pubkey_value, sizeof(pubkey_value)}, + }; + CK_ULONG extr_tmpl_len = sizeof(extr_tmpl)/sizeof(CK_ATTRIBUTE); + + CK_OBJECT_CLASS class = CKO_SECRET_KEY; + CK_KEY_TYPE key_type = CKK_GENERIC_SECRET; + CK_BBOOL true = CK_TRUE; + CK_BBOOL false = CK_FALSE; + CK_ATTRIBUTE derive_tmpl[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &key_type, sizeof(key_type)}, + {CKA_SENSITIVE, &false, sizeof(false)}, + {CKA_VALUE_LEN, &secret_key_len, sizeof(CK_ULONG)}, + {CKA_IBM_USE_AS_DATA, &true, sizeof(true)}, + }; + CK_ULONG secret_tmpl_len = + sizeof(derive_tmpl) / sizeof(CK_ATTRIBUTE); + + if (!mech_supported(SLOT_ID, CKM_EC_KEY_PAIR_GEN)) { + testcase_notice("Slot %u doesn't support CKM_EC_KEY_PAIR_GEN\n", + (unsigned int) SLOT_ID); + return CKR_FUNCTION_NOT_SUPPORTED; + } + + rc = generate_EC_KeyPair(session, (CK_BYTE *)prime256v1, sizeof(prime256v1), + &publ_key, &priv_key); + if (rc != CKR_OK) { + testcase_notice("generate_EC_KeyPair rc=%s", p11_get_ckr(rc)); + goto error; + } + + rc = funcs->C_GetAttributeValue(session, publ_key, extr_tmpl, extr_tmpl_len); + if (rc != CKR_OK) { + testcase_notice("C_GetAttributeValue: rc = %s", p11_get_ckr(rc)); + goto error; + } + + mech.mechanism = CKM_ECDH1_DERIVE; + mech.pParameter = &ecda_params; + mech.ulParameterLen = sizeof(ecda_params); + + memset(&ecda_params, 0, sizeof(ecda_params)); + ecda_params.kdf = kdf; + ecda_params.pPublicData = extr_tmpl[0].pValue; + ecda_params.ulPublicDataLen = extr_tmpl[0].ulValueLen; + + rc = funcs->C_DeriveKey(session, &mech, priv_key, derive_tmpl, + secret_tmpl_len, hybrid_key); + if (rc != CKR_OK) { + testcase_notice("C_DeriveKey: rc = %s", p11_get_ckr(rc)); + goto error; + } + +error: + if (publ_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, publ_key); + if (priv_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, priv_key); + + return rc; +} + +CK_RV run_EnDecapsulateKyber(CK_SESSION_HANDLE session, + CK_OBJECT_HANDLE priv_key, + CK_OBJECT_HANDLE publ_key, + CK_ULONG secret_key_len, + CK_IBM_KYBER_KDF_TYPE kdf, + CK_BBOOL hybrid, + const CK_BYTE *pSharedData, + CK_ULONG ulSharedDataLen, + const CK_BYTE *pCipher, + CK_ULONG ulCipherLen, + const CK_BYTE *pExpectedSecret, + CK_ULONG ulExpectedSecret) +{ + CK_MECHANISM mech; + CK_MECHANISM_INFO mech_info; + CK_IBM_KYBER_PARAMS kyber_params; + CK_BYTE *cipher = NULL; + CK_ULONG cipher_len = 0; + CK_OBJECT_HANDLE secret_key1 = CK_INVALID_HANDLE; + CK_OBJECT_HANDLE secret_key2 = CK_INVALID_HANDLE; + CK_OBJECT_HANDLE hybrid_key = CK_INVALID_HANDLE; + CK_OBJECT_HANDLE expected_secret_key = CK_INVALID_HANDLE; + CK_RV rc; + + CK_OBJECT_CLASS class = CKO_SECRET_KEY; + CK_KEY_TYPE key_type = CKK_GENERIC_SECRET; + CK_BBOOL true = CK_TRUE; + CK_BBOOL false = CK_FALSE; + CK_ATTRIBUTE derive_tmpl[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &key_type, sizeof(key_type)}, + {CKA_SENSITIVE, &false, sizeof(false)}, + {CKA_VALUE_LEN, &secret_key_len, sizeof(secret_key_len)}, + {CKA_SIGN, &true, sizeof(true)}, + {CKA_VERIFY, &true, sizeof(true)}, + }; + CK_ULONG secret_tmpl_len = sizeof(derive_tmpl) / sizeof(CK_ATTRIBUTE); + + mech.mechanism = CKM_IBM_KYBER; + mech.ulParameterLen = sizeof(kyber_params); + mech.pParameter = &kyber_params; + + /* Query the slot, check if this mech if supported */ + rc = funcs->C_GetMechanismInfo(SLOT_ID, mech.mechanism, &mech_info); + if (rc != CKR_OK) { + if (rc == CKR_MECHANISM_INVALID) { + /* no support for Kyber? skip */ + testcase_skip("Slot %u doesn't support %s", + (unsigned int) SLOT_ID, + p11_get_ckm(&mechtable_funcs, mech.mechanism)); + rc = CKR_OK; + goto testcase_cleanup; + } else { + testcase_error("C_GetMechanismInfo() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + + if (hybrid) { + rc = ecdh_derive_secret(session, 32, CKD_IBM_HYBRID_NULL, &hybrid_key); + if (rc != CKR_OK) { + testcase_error("ecdh_derive_secret() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + + if (pCipher != NULL && ulCipherLen != 0) { + cipher_len = ulCipherLen; + cipher = (CK_BYTE *)pCipher; + goto decapsulate; + } + + /* Perform encapsulation with public key */ + memset(&kyber_params, 0, sizeof(kyber_params)); + kyber_params.ulVersion = CK_IBM_KYBER_KEM_VERSION; + kyber_params.mode = CK_IBM_KYBER_KEM_ENCAPSULATE; + kyber_params.kdf = kdf; + kyber_params.pSharedData = (CK_BYTE *)pSharedData; + kyber_params.ulSharedDataLen = ulSharedDataLen; + kyber_params.bPrepend = (hybrid_key != CK_INVALID_HANDLE); + kyber_params.hSecret = hybrid_key; + + /* Size query */ + rc = funcs->C_DeriveKey(session, &mech, publ_key, derive_tmpl, + secret_tmpl_len, &secret_key1); + if (rc != CKR_BUFFER_TOO_SMALL) { + testcase_error("C_DeriveKey (size query) rc=%s (expected CKR_BUFFER_TOO_SMALL)", + p11_get_ckr(rc)); + goto testcase_cleanup; + } + + cipher_len = kyber_params.ulCipherLen; + cipher = calloc(sizeof(CK_BYTE), cipher_len); + if (cipher == NULL) { + testcase_error("Can't allocate memory for %lu bytes", + sizeof(CK_BYTE) * cipher_len); + rc = CKR_HOST_MEMORY; + goto testcase_cleanup; + } + + kyber_params.ulCipherLen = cipher_len; + kyber_params.pCipher = cipher; + + /* Encapsulation */ + rc = funcs->C_DeriveKey(session, &mech, publ_key, derive_tmpl, + secret_tmpl_len, &secret_key1); + if (rc != CKR_OK) { + testcase_error("C_DeriveKey (encapsulation) rc=%s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + +decapsulate: + /* Perform Decapsulation with private key */ + memset(&kyber_params, 0, sizeof(kyber_params)); + kyber_params.ulVersion = CK_IBM_KYBER_KEM_VERSION; + kyber_params.mode = CK_IBM_KYBER_KEM_DECAPSULATE; + kyber_params.kdf = kdf; + kyber_params.pSharedData = (CK_BYTE *)pSharedData; + kyber_params.ulSharedDataLen = ulSharedDataLen; + kyber_params.bPrepend = (hybrid_key != CK_INVALID_HANDLE); + kyber_params.hSecret = hybrid_key; + kyber_params.ulCipherLen = cipher_len; + kyber_params.pCipher = cipher; + + rc = funcs->C_DeriveKey(session, &mech, priv_key, derive_tmpl, + secret_tmpl_len, &secret_key2); + if (rc != CKR_OK) { + testcase_error("C_DeriveKey (decapsulation) rc=%s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (secret_key1 != CK_INVALID_HANDLE) { + rc = run_HMACSign(session, secret_key1, secret_key2, secret_key_len); + if (rc != CKR_OK) { + testcase_fail("Derived keys are not usable or not the same: %s", + p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + + if (pExpectedSecret != NULL && ulExpectedSecret != 0) { + rc = create_GenericSecretKey(session, (CK_BYTE *)pExpectedSecret, + ulExpectedSecret, &expected_secret_key); + if (rc != CKR_OK) { + testcase_fail("create_GenericSecretKey failed: %s", + p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = run_HMACSign(session, expected_secret_key, secret_key2, + secret_key_len); + if (rc != CKR_OK) { + testcase_fail("Derived secret key is not the expected one: %s", + p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + + rc = CKR_OK; + +testcase_cleanup: + if (cipher != NULL && cipher != pCipher) + free(cipher); + if (secret_key1 != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, secret_key1); + if (secret_key2 != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, secret_key2); + if (hybrid_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, hybrid_key); + if (expected_secret_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, expected_secret_key); + + return rc; +} + +CK_RV run_EncrypDecryptKyber(CK_SESSION_HANDLE session, + CK_OBJECT_HANDLE priv_key, + CK_OBJECT_HANDLE publ_key) +{ + CK_MECHANISM mech; + CK_BYTE_PTR data = NULL, encrypted = NULL, decrypted = NULL; + CK_ULONG i, datalen, encrypted_len, decrypted_len; + CK_MECHANISM_INFO mech_info; + CK_RV rc; + + mech.mechanism = CKM_IBM_KYBER; + mech.ulParameterLen = 0; + mech.pParameter = NULL; + + datalen = 32; /* Kyber can encrypt blocks of 32 bytes */ + + /* Query the slot, check if this mech if supported */ + rc = funcs->C_GetMechanismInfo(SLOT_ID, mech.mechanism, &mech_info); + if (rc != CKR_OK) { + if (rc == CKR_MECHANISM_INVALID) { + /* no support for Kyber? skip */ + testcase_skip("Slot %u doesn't support %s", + (unsigned int) SLOT_ID, + p11_get_ckm(&mechtable_funcs, mech.mechanism)); + rc = CKR_OK; + goto testcase_cleanup; + } else { + testcase_error("C_GetMechanismInfo() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + + data = calloc(sizeof(CK_BYTE), datalen); + if (data == NULL) { + testcase_error("Can't allocate memory for %lu bytes", + sizeof(CK_BYTE) * datalen); + rc = CKR_HOST_MEMORY; + goto testcase_cleanup; + } + + for (i = 0; i < datalen; i++) { + data[i] = (i + 1) % 255; + } + + /* Encrypt */ + rc = funcs->C_EncryptInit(session, &mech, publ_key); + if (rc != CKR_OK) { + testcase_error("C_EncryptInit rc=%s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = funcs->C_Encrypt(session, data, datalen, NULL, &encrypted_len); + if (rc != CKR_OK) { + testcase_error("C_Encrypt rc=%s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + encrypted = calloc(sizeof(CK_BYTE), encrypted_len); + if (encrypted == NULL) { + testcase_error("Can't allocate memory for %lu bytes", + sizeof(CK_BYTE) * encrypted_len); + rc = CKR_HOST_MEMORY; + goto testcase_cleanup; + } + + rc = funcs->C_Encrypt(session, data, datalen, encrypted, &encrypted_len); + if (rc != CKR_OK) { + testcase_error("C_Encrypt rc=%s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* Decrypt */ + rc = funcs->C_DecryptInit(session, &mech, priv_key); + if (rc != CKR_OK) { + testcase_error("C_DecryptInit rc=%s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = funcs->C_Decrypt(session, encrypted, encrypted_len, + NULL, &decrypted_len); + if (rc != CKR_OK) { + testcase_error("C_Decrypt rc=%s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + decrypted = calloc(sizeof(CK_BYTE), decrypted_len); + if (decrypted == NULL) { + testcase_error("Can't allocate memory for %lu bytes", + sizeof(CK_BYTE) * decrypted_len); + rc = CKR_HOST_MEMORY; + goto testcase_cleanup; + } + + rc = funcs->C_Decrypt(session, encrypted, encrypted_len, + decrypted, &decrypted_len); + if (rc != CKR_OK) { + testcase_error("C_Decrypt rc=%s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (decrypted_len != datalen || + memcmp(decrypted, data, datalen) != 0) { + testcase_error("Decrypted data (%lu bytes) does not match original data (%lu bytes)", + decrypted_len, datalen); + goto testcase_cleanup; + } + + rc = CKR_OK; + +testcase_cleanup: + if (data) + free(data); + if (encrypted) + free(encrypted); + if (decrypted) + free(decrypted); + + return rc; +} + +CK_RV run_GenerateKyberKeyPairEnDecryptKEM(void) +{ + CK_MECHANISM mech; + CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; + CK_SESSION_HANDLE session; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len, i, j; + CK_FLAGS flags; + CK_MECHANISM_INFO mech_info; + CK_RV rc; + + testcase_rw_session(); + testcase_user_login(); + + mech.mechanism = CKM_IBM_KYBER; + mech.ulParameterLen = 0; + mech.pParameter = NULL; + + /* query the slot, check if this mech is supported */ + rc = funcs->C_GetMechanismInfo(SLOT_ID, mech.mechanism, &mech_info); + if (rc != CKR_OK) { + if (rc == CKR_MECHANISM_INVALID) { + /* no support for Kyber key gen? skip */ + testcase_skip("Slot %u doesn't support CKM_IBM_KYBER ", + (unsigned int) SLOT_ID); + rc = CKR_OK; + goto testcase_cleanup; + } else { + testcase_error("C_GetMechanismInfo() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + + for (i = 0; i < 2 * num_variants; i++) { + /* Setup attributes for public/private Kyber key */ + CK_BBOOL attr_enc = TRUE; + CK_BBOOL attr_dec = TRUE; + CK_BBOOL attr_derive = TRUE; + CK_ATTRIBUTE kyber_attr_private_keyform[] = { + {CKA_DECRYPT, &attr_dec, sizeof(CK_BBOOL)}, + {CKA_DERIVE, &attr_derive, sizeof(CK_BBOOL)}, + {CKA_IBM_KYBER_KEYFORM, + (CK_BYTE *)&variants[i % num_variants].keyform, sizeof(CK_ULONG)}, + }; + CK_ATTRIBUTE kyber_attr_public_keyform[] = { + {CKA_ENCRYPT, &attr_enc, sizeof(CK_BBOOL)}, + {CKA_DERIVE, &attr_derive, sizeof(CK_BBOOL)}, + {CKA_IBM_KYBER_KEYFORM, + (CK_BYTE *)&variants[i % num_variants].keyform, sizeof(CK_ULONG)}, + }; + CK_ATTRIBUTE kyber_attr_private_mode[] = { + {CKA_DECRYPT, &attr_dec, sizeof(CK_BBOOL)}, + {CKA_DERIVE, &attr_derive, sizeof(CK_BBOOL)}, + {CKA_IBM_KYBER_MODE, + (CK_BYTE *)variants[i % num_variants].oid, variants[i % num_variants].oid_len}, + }; + CK_ATTRIBUTE kyber_attr_public_mode[] = { + {CKA_ENCRYPT, &attr_enc, sizeof(CK_BBOOL)}, + {CKA_DERIVE, &attr_derive, sizeof(CK_BBOOL)}, + {CKA_IBM_KYBER_MODE, + (CK_BYTE *)variants[i % num_variants].oid, variants[i % num_variants].oid_len}, + }; + CK_ATTRIBUTE *kyber_attr_private = i < num_variants ? + kyber_attr_private_keyform : + kyber_attr_private_mode; + CK_ATTRIBUTE *kyber_attr_public = i < num_variants ? + kyber_attr_public_keyform : + kyber_attr_public_mode; + CK_ULONG num_kyber_attrs = + (variants[i % num_variants].oid == NULL) ? 2 : 3; + + testcase_begin("Starting Kyber generate key pair with %s.", + variants[i % num_variants].name); + + /* Generate Kyber key pair */ + rc = funcs->C_GenerateKeyPair(session, &mech, + kyber_attr_public, num_kyber_attrs, + kyber_attr_private, num_kyber_attrs, + &publ_key, &priv_key); + testcase_new_assertion(); + if (rc != CKR_OK) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_GenerateKeyPair with %s (%s) not supported", + variants[i % num_variants].name, + i < num_variants ? "KEYFORM" : "MODE"); + goto next; + } else { + testcase_fail("C_GenerateKeyPair with %s (%s) failed, rc=%s", + variants[i % num_variants].name, + i < num_variants ? "KEYFORM" : "MODE", p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + testcase_pass("*Generate Kyber key pair with %s (%s) passed.", + variants[i % num_variants].name, + i < num_variants ? "KEYFORM" : "MODE"); + + testcase_new_assertion(); + rc = run_EncrypDecryptKyber(session, priv_key, publ_key); + if (rc != 0) { + testcase_fail("run_EncrypDecryptKyber with %s failed.", + variants[i % num_variants].name); + goto next; + } + testcase_pass("*Encrypt & decrypt with %s passed.", + variants[i % num_variants].name); + + for (j = 0; j < NUM_KEM_INPUTS; j++) { + testcase_new_assertion(); + rc = run_EnDecapsulateKyber(session, priv_key, publ_key, + kemInput[j].secret_key_len, + kemInput[j].kdf, + kemInput[j].hybrid, + kemInput[j].shared_data, + kemInput[j].shard_data_len, + NULL, 0, NULL, 0); + if (rc != 0) { + testcase_fail("run_EnDecapsulateKyber with %s, %s, Shared data len %lu (index %lu) failed.", + variants[i % num_variants].name, + p11_get_ckd(kemInput[j].kdf), + kemInput[j].shard_data_len, + j); + goto next; + } + testcase_pass("*%sEncapsulate & Decapsulate (KEM) with %s, %s, Shared data len %lu (index %lu) passed.", + kemInput[j].hybrid ? "Hybrid " : "", + variants[i % num_variants].name, + p11_get_ckd(kemInput[j].kdf), + kemInput[j].shard_data_len, + j); + } + +next: + if (publ_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, publ_key); + publ_key = CK_INVALID_HANDLE; + if (priv_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, priv_key); + priv_key = CK_INVALID_HANDLE; + } + + rc = CKR_OK; + +testcase_cleanup: + if (publ_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, publ_key); + if (priv_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, priv_key); + + testcase_user_logout(); + testcase_close_session(); + + return rc; +} + +CK_RV run_ImportKyberKeyPairKEM(void) +{ + CK_MECHANISM mech; + CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; + CK_SESSION_HANDLE session; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len, i; + CK_FLAGS flags; + CK_MECHANISM_INFO mech_info; + CK_RV rc; + + testcase_rw_session(); + testcase_user_login(); + + mech.mechanism = CKM_IBM_KYBER; + mech.ulParameterLen = 0; + mech.pParameter = NULL; + + /* query the slot, check if this mech is supported */ + rc = funcs->C_GetMechanismInfo(SLOT_ID, mech.mechanism, &mech_info); + if (rc != CKR_OK) { + if (rc == CKR_MECHANISM_INVALID) { + /* no support for Kyber key gen? skip */ + testcase_skip("Slot %u doesn't support CKM_IBM_KYBER", + (unsigned int) SLOT_ID); + goto testcase_cleanup; + } else { + testcase_error("C_GetMechanismInfo() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + + for (i = 0; i < KYBER_TV_NUM; i++) { + + testcase_begin("Starting Kyber import key pair, KEM, %s index=%lu", + kyber_tv[i].name, i); + + /* Create Kyber private key */ + rc = create_KyberPrivateKey(session, + kyber_tv[i].pkcs8, kyber_tv[i].pkcs8_len, + kyber_tv[i].keyform, + kyber_tv[i].sk, kyber_tv[i].sk_len, + kyber_tv[i].pk, kyber_tv[i].pk_len, + &priv_key); + testcase_new_assertion(); + if (rc != CKR_OK) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_CreateObject with key form %lu not supported", + kyber_tv[i].keyform); + continue; + } + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("Kyber key import is not allowed by policy"); + continue; + } + testcase_fail("C_CreateObject (Kyber Private Key) failed at i=%lu, " + "rc=%s", i, p11_get_ckr(rc)); + goto next; + } + testcase_pass("*Import Kyber private key (%s) index=%lu passed.", + kyber_tv[i].name, i); + + /* Create Kyber public key */ + rc = create_KyberPublicKey(session, + kyber_tv[i].spki, kyber_tv[i].spki_len, + kyber_tv[i].keyform, + kyber_tv[i].pk, kyber_tv[i].pk_len, + &publ_key); + testcase_new_assertion(); + if (rc != CKR_OK) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_CreateObject with key form %lu not supported", + kyber_tv[i].keyform); + continue; + } + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("Kyber key import is not allowed by policy"); + goto testcase_cleanup; + } + testcase_fail("C_CreateObject (Kyber Public Key) failed at i=%lu, " + "rc=%s", i, p11_get_ckr(rc)); + goto next; + } + testcase_pass("*Import Kyber public key (%s) index=%lu passed.", + kyber_tv[i].name, i); + + testcase_new_assertion(); + rc = run_EnDecapsulateKyber(session, priv_key, publ_key, + kyber_tv[i].secret_len, + CKD_NULL, CK_FALSE, NULL, 0, + kyber_tv[i].cipher, kyber_tv[i].cipher_len, + kyber_tv[i].secret, kyber_tv[i].secret_len); + if (rc != 0) { + testcase_fail("run_EnDecapsulateKyber with %s failed.", + variants[i % num_variants].name); + goto next; + } + testcase_pass("*Encapsulate & Decapsulate (KEM) with %s index=%lu passed.", + variants[i % num_variants].name, i); + + +next: + /* Clean up */ + rc = funcs->C_DestroyObject(session, publ_key); + if (rc != CKR_OK) { + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(rc)); + } + + rc = funcs->C_DestroyObject(session, priv_key); + if (rc != CKR_OK) { + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(rc)); + } + } + + goto done; + +testcase_cleanup: + if (publ_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, publ_key); + if (priv_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, priv_key); + +done: + testcase_user_logout(); + testcase_close_session(); + + return rc; +} + +/** + * Wraps the given key with the given secret key using the given wrapping + * mechanism. + */ +CK_RV wrapKey(CK_SESSION_HANDLE session, CK_MECHANISM *wrap_mech, + CK_OBJECT_HANDLE secret_key, CK_OBJECT_HANDLE key_to_wrap, + CK_BYTE_PTR *wrapped_key, CK_ULONG *wrapped_keylen) +{ + CK_BYTE_PTR tmp_key; + CK_ULONG tmp_len; + CK_RV rc; + + /* Determine length of wrapped key */ + rc = funcs->C_WrapKey(session, wrap_mech, secret_key, key_to_wrap, + NULL, &tmp_len); + if (rc != CKR_OK) + goto done; + + /* Allocate memory for wrapped_key */ + tmp_key = calloc(sizeof(CK_BYTE), tmp_len); + if (!tmp_key) { + rc = CKR_HOST_MEMORY; + goto done; + } + + /* Now wrap the key */ + rc = funcs->C_WrapKey(session, wrap_mech, secret_key, key_to_wrap, + tmp_key, &tmp_len); + if (rc != CKR_OK) { + free(tmp_key); + tmp_key = NULL; + goto done; + } + + *wrapped_key = tmp_key; + *wrapped_keylen = tmp_len; + + rc = CKR_OK; + +done: + + return rc; +} + +/** + * Unwraps the given wrapped_key using the given secret_key and wrapping + * mechanism. + */ +CK_RV unwrapKey(CK_SESSION_HANDLE session, CK_MECHANISM *wrap_mech, + CK_BYTE_PTR wrapped_key, CK_ULONG wrapped_keylen, + CK_OBJECT_HANDLE secret_key, CK_OBJECT_HANDLE *unwrapped_key) +{ + CK_OBJECT_CLASS class = CKO_PRIVATE_KEY; + CK_KEY_TYPE key_type = CKK_IBM_PQC_KYBER; + CK_OBJECT_HANDLE tmp_key = CK_INVALID_HANDLE; + CK_BYTE unwrap_label[] = "unwrapped_private_Kyber_Key"; + CK_BYTE subject[] = {0}; + CK_BYTE id[] = { 123 }; + CK_BBOOL true = TRUE; + CK_RV rc; + + CK_ATTRIBUTE unwrap_tmpl[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &key_type, sizeof(key_type)}, + {CKA_TOKEN, &true, sizeof(true)}, + {CKA_LABEL, &unwrap_label, sizeof(unwrap_label)}, + {CKA_SUBJECT, subject, sizeof(subject)}, + {CKA_ID, id, sizeof(id)}, + {CKA_SENSITIVE, &true, sizeof(true)}, + {CKA_DECRYPT, &true, sizeof(true)}, + {CKA_DERIVE, &true, sizeof(true)}, + }; + + rc = funcs->C_UnwrapKey(session, wrap_mech, secret_key, + wrapped_key, wrapped_keylen, + unwrap_tmpl, + sizeof(unwrap_tmpl) / sizeof(CK_ATTRIBUTE), + &tmp_key); + if (rc != CKR_OK) + goto done; + + *unwrapped_key = tmp_key; + + rc = CKR_OK; + +done: + + return rc; +} + +CK_RV run_TransferKyberKeyPair(void) +{ + CK_MECHANISM mech; + CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; + CK_SESSION_HANDLE session; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len, i; + CK_FLAGS flags; + CK_MECHANISM_INFO mech_info; + CK_RV rc; + CK_OBJECT_HANDLE secret_key = CK_INVALID_HANDLE; + CK_BYTE_PTR wrapped_key = NULL; + CK_ULONG wrapped_keylen; + CK_OBJECT_HANDLE unwrapped_key = CK_INVALID_HANDLE; + CK_MECHANISM wrap_mech, wkey_mech; + + testcase_rw_session(); + testcase_user_login(); + + mech.mechanism = CKM_IBM_KYBER; + mech.ulParameterLen = 0; + mech.pParameter = NULL; + + /* query the slot, check if this mech is supported */ + rc = funcs->C_GetMechanismInfo(SLOT_ID, mech.mechanism, &mech_info); + if (rc != CKR_OK) { + if (rc == CKR_MECHANISM_INVALID) { + /* no support for Kyber key gen? skip */ + testcase_skip("Slot %u doesn't support CKM_IBM_KYBER", + (unsigned int) SLOT_ID); + goto testcase_cleanup; + } else { + testcase_error("C_GetMechanismInfo() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + } + + for (i = 0; i < KYBER_TV_NUM; i++) { + + testcase_begin("Starting Kyber transfer key pair, Encrypt/Decrypt %s index=%lu.", + kyber_tv[i].name, i); + + /* Create Kyber private key */ + rc = create_KyberPrivateKey(session, + kyber_tv[i].pkcs8, kyber_tv[i].pkcs8_len, + kyber_tv[i].keyform, + kyber_tv[i].sk, kyber_tv[i].sk_len, + kyber_tv[i].pk, kyber_tv[i].pk_len, + &priv_key); + + testcase_new_assertion(); + if (rc != CKR_OK) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_CreateObject with key form %lu not supported", + kyber_tv[i].keyform); + continue; + } + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("Kyber key import is not allowed by policy"); + continue; + } + testcase_fail + ("C_CreateObject (Kyber Private Key) failed at i=%lu, rc=%s", i, + p11_get_ckr(rc)); + goto next; + } + testcase_pass("*Import Kyber private key (%s) index=%lu passed.", + kyber_tv[i].name, i); + + /* Create Kyber public key */ + rc = create_KyberPublicKey(session, + kyber_tv[i].spki, kyber_tv[i].spki_len, + kyber_tv[i].keyform, + kyber_tv[i].pk, kyber_tv[i].pk_len, + &publ_key); + testcase_new_assertion(); + if (rc != CKR_OK) { + if (rc == CKR_KEY_SIZE_RANGE) { + testcase_skip("C_CreateObject with key form %lu not supported", + kyber_tv[i].keyform); + continue; + } + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("Kyber key import is not allowed by policy"); + goto testcase_cleanup; + } + testcase_fail + ("C_CreateObject (Kyber Public Key) failed at i=%lu, rc=%s", i, + p11_get_ckr(rc)); + goto next; + } + testcase_pass("*Import Kyber public key (%s) index=%lu passed.", + kyber_tv[i].name, i); + + /* Create wrapping key (secret key) */ + wkey_mech.mechanism = CKM_AES_KEY_GEN; + wkey_mech.pParameter = NULL; + wkey_mech.ulParameterLen = 0; + rc = generate_AESKey(session, 32, CK_TRUE, &wkey_mech, &secret_key); + if (rc != CKR_OK) { + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("AES key generation is not allowed by policy"); + goto testcase_cleanup; + } + + testcase_error("generate_AESKey, rc=%s", p11_get_ckr(rc)); + goto next; + } + + /* Setup wrapping mechanism */ + wrap_mech.mechanism = CKM_AES_CBC_PAD; + wrap_mech.pParameter = "0123456789abcdef"; + wrap_mech.ulParameterLen = 16; + + /* Wrap Kyber private key with secret key */ + rc = wrapKey(session, &wrap_mech, secret_key, priv_key, + &wrapped_key, &wrapped_keylen); + testcase_new_assertion(); + if (rc != CKR_OK) { + testcase_error("wrapKey, rc=%s", p11_get_ckr(rc)); + goto next; + } + testcase_pass("*Wrap Kyber private key (%s) index=%lu passed.", + kyber_tv[i].name, i); + + /* Unwrap Kyber private key */ + rc = unwrapKey(session, &wrap_mech, wrapped_key, wrapped_keylen, + secret_key, &unwrapped_key); + testcase_new_assertion(); + if (rc != CKR_OK) { + testcase_error("unwrapKey, rc=%s", p11_get_ckr(rc)); + goto next; + } + testcase_pass("*Unwrap Kyber private key (%s) index=%lu passed.", + kyber_tv[i].name, i); + + free(wrapped_key); + wrapped_key = NULL; + + /* Encrypt/Decrypt with unwrapped key */ + testcase_new_assertion(); + rc = run_EncrypDecryptKyber(session, unwrapped_key, publ_key); + if (rc != 0) { + testcase_fail("run_EncrypDecryptKyber with %s failed.", + kyber_tv[i].name); + goto next; + } + testcase_pass("*Encrypt & decrypt with unwrapped private key with %s index=%lu passed.", + kyber_tv[i].name, i); + + testcase_new_assertion(); + rc = run_EnDecapsulateKyber(session, unwrapped_key, publ_key, + kyber_tv[i].secret_len, + CKD_NULL, CK_FALSE, NULL, 0, + kyber_tv[i].cipher, kyber_tv[i].cipher_len, + kyber_tv[i].secret, kyber_tv[i].secret_len); + if (rc != 0) { + testcase_fail("run_EnDecapsulateKyber with %s failed.", + variants[i % num_variants].name); + goto next; + } + testcase_pass("*Encapsulate & Decapsulate (KEM) with unwrapped private key with %s index=%lu passed.", + variants[i % num_variants].name, i); + +next: + /* Clean up */ + rc = funcs->C_DestroyObject(session, publ_key); + if (rc != CKR_OK) { + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(rc)); + } + + rc = funcs->C_DestroyObject(session, priv_key); + if (rc != CKR_OK) { + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(rc)); + } + + rc = funcs->C_DestroyObject(session, secret_key); + if (rc != CKR_OK) { + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(rc)); + } + + rc = funcs->C_DestroyObject(session, unwrapped_key); + if (rc != CKR_OK) { + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(rc)); + } + } + + goto done; + +testcase_cleanup: + if (publ_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, publ_key); + if (priv_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, priv_key); + if (secret_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, secret_key); + if (unwrapped_key != CK_INVALID_HANDLE) + funcs->C_DestroyObject(session, unwrapped_key); + + if (wrapped_key) + free(wrapped_key); + +done: + testcase_user_logout(); + testcase_close_session(); + + return rc; +} + +int main(int argc, char **argv) +{ + CK_C_INITIALIZE_ARGS cinit_args; + int rc; + CK_RV rv; + + rc = do_ParseArgs(argc, argv); + if (rc != 1) + return rc; + + printf("Using slot #%lu...\n\n", SLOT_ID); + printf("With option: no_init: %d\n", no_init); + + rc = do_GetFunctionList(); + if (!rc) { + PRINT_ERR("ERROR do_GetFunctionList() Failed , rc = 0x%0x\n", rc); + return rc; + } + + memset(&cinit_args, 0x0, sizeof(cinit_args)); + cinit_args.flags = CKF_OS_LOCKING_OK; + + funcs->C_Initialize(&cinit_args); + + { + CK_SESSION_HANDLE hsess = 0; + + rc = funcs->C_GetFunctionStatus(hsess); + if (rc != CKR_FUNCTION_NOT_PARALLEL) + return rc; + + rc = funcs->C_CancelFunction(hsess); + if (rc != CKR_FUNCTION_NOT_PARALLEL) + return rc; + } + + testcase_setup(); + + rv = run_GenerateKyberKeyPairEnDecryptKEM(); + + rv = run_ImportKyberKeyPairKEM(); + + rv = run_TransferKyberKeyPair(); + + testcase_print_result(); + + funcs->C_Finalize(NULL); + + return testcase_return(rv); +} diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/kyber.h opencryptoki-3.20.0+dfsg/testcases/crypto/kyber.h --- opencryptoki-3.18.0+dfsg/testcases/crypto/kyber.h 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/kyber.h 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,1406 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +/** + * Experimental Support for Kyber keys and KEM + * with oid = 1.3.6.1.4.1.2.267.5.xxx + * + * Public-key encoding; raw public-key field. See RFC 3279 for + * subjectPublicKeyInfo (SPKI) structures. + * + * KyberPublicKey ::= BIT STRING { + * SEQUENCE { + * pk BIT STRING -- public key + * } + * } + * + * Private-key encoding; see RFC 5959 for PKCS#8 structure definitions. + * + * KyberPrivateKey ::= SEQUENCE { + * version INTEGER, -- v0; reserved 0 + * sk BIT STRING, -- privet key + * pk [0] IMPLICIT OPTIONAL { + * pk BIT STRING -- public key + * } + * } + */ + +struct KYBER_TEST_VECTOR { + char *name; + int version; + CK_ULONG keyform; + CK_ULONG sk_len; + CK_BYTE sk[4096]; + CK_ULONG pk_len; + CK_BYTE pk[4096]; + CK_BYTE pkcs8[8192]; + CK_ULONG pkcs8_len; + CK_BYTE spki[8192]; + CK_ULONG spki_len; + CK_BYTE secret[32]; + CK_ULONG secret_len; + CK_BYTE cipher[2048]; + CK_ULONG cipher_len; +}; + +/** + * test vectors from: https://csrc.nist.gov/Projects/post-quantum-cryptography/round-2-submissions + */ +struct KYBER_TEST_VECTOR kyber_tv[] = { + { + .name = "Kyber Round 2, 786 KAT 0 (PKCS#8/SPKI)", + .version = 0, + .keyform = 0, + .pk_len = 0, + .sk_len = 0, + .pkcs8_len = 3697, + .pkcs8 = { + 0x30, 0x82, 0x0e, 0x6d, 0x02, 0x01, 0x00, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x05, 0x03, 0x03, 0x05, 0x00, 0x04, 0x82, 0x0e, 0x55, 0x30, 0x82, 0x0e, 0x51, + 0x02, 0x01, 0x00, 0x03, 0x82, 0x09, 0x61, 0x00, 0x07, 0x63, 0x8f, 0xb6, 0x98, 0x68, 0xf3, 0xd3, 0x20, 0xe5, 0x86, 0x2b, 0xd9, 0x69, 0x33, 0xfe, 0xb3, 0x11, 0xb3, 0x62, 0x09, 0x3c, 0x9b, 0x5d, + 0x50, 0x17, 0x0b, 0xce, 0xd4, 0x3f, 0x1b, 0x53, 0x6d, 0x9a, 0x20, 0x4b, 0xb1, 0xf2, 0x26, 0x95, 0x95, 0x0b, 0xa1, 0xf2, 0xa9, 0xe8, 0xeb, 0x82, 0x8b, 0x28, 0x44, 0x88, 0x76, 0x0b, 0x3f, 0xc8, + 0x4f, 0xab, 0xa0, 0x42, 0x75, 0xd5, 0x62, 0x8e, 0x39, 0xc5, 0xb2, 0x47, 0x13, 0x74, 0x28, 0x3c, 0x50, 0x32, 0x99, 0xc0, 0xab, 0x49, 0xb6, 0x6b, 0x8b, 0xbb, 0x56, 0xa4, 0x18, 0x66, 0x24, 0xf9, + 0x19, 0xa2, 0xba, 0x59, 0xbb, 0x08, 0xd8, 0x55, 0x18, 0x80, 0xc2, 0xbe, 0xfc, 0x4f, 0x87, 0xf2, 0x5f, 0x59, 0xab, 0x58, 0x7a, 0x79, 0xc3, 0x27, 0xd7, 0x92, 0xd5, 0x4c, 0x97, 0x4a, 0x69, 0x26, + 0x2f, 0xf8, 0xa7, 0x89, 0x38, 0x28, 0x9e, 0x9a, 0x87, 0xb6, 0x88, 0xb0, 0x83, 0xe0, 0x59, 0x5f, 0xe2, 0x18, 0xb6, 0xbb, 0x15, 0x05, 0x94, 0x1c, 0xe2, 0xe8, 0x1a, 0x5a, 0x64, 0xc5, 0xaa, 0xc6, + 0x04, 0x17, 0x25, 0x69, 0x85, 0x34, 0x9e, 0xe4, 0x7a, 0x52, 0x42, 0x0a, 0x5f, 0x97, 0x47, 0x7b, 0x72, 0x36, 0xac, 0x76, 0xbc, 0x70, 0xe8, 0x28, 0x87, 0x29, 0x28, 0x7e, 0xe3, 0xe3, 0x4a, 0x3d, + 0xbc, 0x36, 0x83, 0xc0, 0xb7, 0xb1, 0x00, 0x29, 0xfc, 0x20, 0x34, 0x18, 0x53, 0x7e, 0x74, 0x66, 0xba, 0x63, 0x85, 0xa8, 0xff, 0x30, 0x1e, 0xe1, 0x27, 0x08, 0xf8, 0x2a, 0xaa, 0x1e, 0x38, 0x0f, + 0xc7, 0xa8, 0x8f, 0x8f, 0x20, 0x5a, 0xb7, 0xe8, 0x8d, 0x7e, 0x95, 0x95, 0x2a, 0x55, 0xba, 0x20, 0xd0, 0x9b, 0x79, 0xa4, 0x71, 0x41, 0xd6, 0x2b, 0xf6, 0xeb, 0x7d, 0xd3, 0x07, 0xb0, 0x8e, 0xca, + 0x13, 0xa5, 0xbc, 0x5f, 0x6b, 0x68, 0x58, 0x1c, 0x68, 0x65, 0xb2, 0x7b, 0xbc, 0xdd, 0xab, 0x14, 0x2f, 0x4b, 0x2c, 0xbf, 0xf4, 0x88, 0xc8, 0xa2, 0x27, 0x05, 0xfa, 0xa9, 0x8a, 0x2b, 0x9e, 0xea, + 0x35, 0x30, 0xc7, 0x66, 0x62, 0x33, 0x5c, 0xc7, 0xea, 0x3a, 0x00, 0x77, 0x77, 0x25, 0xeb, 0xcc, 0xcd, 0x2a, 0x46, 0x36, 0xb2, 0xd9, 0x12, 0x2f, 0xf3, 0xab, 0x77, 0x12, 0x3c, 0xe0, 0x88, 0x3c, + 0x19, 0x11, 0x11, 0x5e, 0x50, 0xc9, 0xe8, 0xa9, 0x41, 0x94, 0xe4, 0x8d, 0xd0, 0xd0, 0x9c, 0xff, 0xb3, 0xad, 0xcd, 0x2c, 0x1e, 0x92, 0x43, 0x09, 0x03, 0xd0, 0x7a, 0xdb, 0xf0, 0x05, 0x32, 0x03, + 0x15, 0x75, 0xaa, 0x7f, 0x9e, 0x7b, 0x5a, 0x1f, 0x33, 0x62, 0xde, 0xc9, 0x36, 0xd4, 0x04, 0x3c, 0x05, 0xf2, 0x47, 0x6c, 0x07, 0x57, 0x8b, 0xc9, 0xcb, 0xaf, 0x2a, 0xb4, 0xe3, 0x82, 0x72, 0x7a, + 0xd4, 0x16, 0x86, 0xa9, 0x6b, 0x25, 0x48, 0x82, 0x0b, 0xb0, 0x3b, 0x32, 0xf1, 0x1b, 0x28, 0x11, 0xad, 0x62, 0xf4, 0x89, 0xe9, 0x51, 0x63, 0x2a, 0xba, 0x0d, 0x1d, 0xf8, 0x96, 0x80, 0xcc, 0x8a, + 0x8b, 0x53, 0xb4, 0x81, 0xd9, 0x2a, 0x68, 0xd7, 0x0b, 0x4e, 0xa1, 0xc3, 0xa6, 0xa5, 0x61, 0xc0, 0x69, 0x28, 0x82, 0xb5, 0xca, 0x8c, 0xc9, 0x42, 0xa8, 0xd4, 0x95, 0xaf, 0xcb, 0x06, 0xde, 0x89, + 0x49, 0x8f, 0xb9, 0x35, 0xb7, 0x75, 0x90, 0x8f, 0xe7, 0xa0, 0x3e, 0x32, 0x4d, 0x54, 0xcc, 0x19, 0xd4, 0xe1, 0xaa, 0xbd, 0x35, 0x93, 0xb3, 0x8b, 0x19, 0xee, 0x13, 0x88, 0xfe, 0x49, 0x2b, 0x43, + 0x12, 0x7e, 0x5a, 0x50, 0x42, 0x53, 0x78, 0x6a, 0x0d, 0x69, 0xad, 0x32, 0x60, 0x1c, 0x28, 0xe2, 0xc8, 0x85, 0x04, 0xa5, 0xba, 0x59, 0x97, 0x06, 0x02, 0x3a, 0x61, 0x36, 0x3e, 0x17, 0xc6, 0xb9, + 0xbb, 0x59, 0xbd, 0xc6, 0x97, 0x45, 0x2c, 0xd0, 0x59, 0x45, 0x19, 0x83, 0xd7, 0x38, 0xca, 0x3f, 0xd0, 0x34, 0xe3, 0xf5, 0x98, 0x88, 0x54, 0xca, 0x05, 0x03, 0x1d, 0xb0, 0x96, 0x11, 0x49, 0x89, + 0x88, 0x19, 0x7c, 0x6b, 0x30, 0xd2, 0x58, 0xdf, 0xe2, 0x62, 0x65, 0x54, 0x1c, 0x89, 0xa4, 0xb3, 0x1d, 0x68, 0x64, 0xe9, 0x38, 0x9b, 0x03, 0xcb, 0x74, 0xf7, 0xec, 0x43, 0x23, 0xfb, 0x94, 0x21, + 0xa4, 0xb9, 0x79, 0x0a, 0x26, 0xd1, 0x7b, 0x03, 0x98, 0xa2, 0x67, 0x67, 0x35, 0x09, 0x09, 0xf8, 0x4d, 0x57, 0xb6, 0x69, 0x4d, 0xf8, 0x30, 0x66, 0x4c, 0xa8, 0xb3, 0xc3, 0xc0, 0x3e, 0xd2, 0xae, + 0x67, 0xb8, 0x90, 0x06, 0x86, 0x8a, 0x68, 0x52, 0x7c, 0xcd, 0x66, 0x64, 0x59, 0xab, 0x7f, 0x05, 0x66, 0x71, 0x00, 0x0c, 0x61, 0x64, 0xd3, 0xa7, 0xf2, 0x66, 0xa1, 0x4d, 0x97, 0xcb, 0xd7, 0x00, + 0x4d, 0x6c, 0x92, 0xca, 0xca, 0x77, 0x0b, 0x84, 0x4a, 0x4f, 0xa9, 0xb1, 0x82, 0xe7, 0xb1, 0x8c, 0xa8, 0x85, 0x08, 0x2a, 0xc5, 0x64, 0x6f, 0xcb, 0x4a, 0x14, 0xe1, 0x68, 0x5f, 0xeb, 0x0c, 0x9c, + 0xe3, 0x37, 0x2a, 0xb9, 0x53, 0x65, 0xc0, 0x4f, 0xd8, 0x30, 0x84, 0xf8, 0x0a, 0x23, 0xff, 0x10, 0xa0, 0x5b, 0xf1, 0x5f, 0x7f, 0xa5, 0xac, 0xc6, 0xc0, 0xcb, 0x46, 0x2c, 0x33, 0xca, 0x52, 0x4f, + 0xa6, 0xb8, 0xbb, 0x35, 0x90, 0x43, 0xba, 0x68, 0x60, 0x9e, 0xaa, 0x25, 0x36, 0xe8, 0x1d, 0x08, 0x46, 0x3b, 0x19, 0x65, 0x3b, 0x54, 0x35, 0xba, 0x94, 0x6c, 0x9a, 0xdd, 0xeb, 0x20, 0x2b, 0x04, + 0xb0, 0x31, 0xcc, 0x96, 0x0d, 0xcc, 0x12, 0xe4, 0x51, 0x8d, 0x42, 0x8b, 0x32, 0xb2, 0x57, 0xa4, 0xfc, 0x73, 0x13, 0xd3, 0xa7, 0x98, 0x0d, 0x80, 0x08, 0x2e, 0x93, 0x4f, 0x9d, 0x95, 0xc3, 0x2b, + 0x0a, 0x01, 0x91, 0xa2, 0x36, 0x04, 0x38, 0x4d, 0xd9, 0xe0, 0x79, 0xbb, 0xba, 0xa2, 0x66, 0xd1, 0x4c, 0x3f, 0x75, 0x6b, 0x9f, 0x21, 0x33, 0x10, 0x74, 0x33, 0xa4, 0xe8, 0x3f, 0xa7, 0x18, 0x72, + 0x82, 0xa8, 0x09, 0x20, 0x3a, 0x4f, 0xaf, 0x84, 0x18, 0x51, 0x83, 0x3d, 0x12, 0x1a, 0xc3, 0x83, 0x84, 0x3a, 0x5e, 0x55, 0xbc, 0x23, 0x81, 0x42, 0x5e, 0x16, 0xc7, 0xdb, 0x4c, 0xc9, 0xab, 0x5c, + 0x1b, 0x0d, 0x91, 0xa4, 0x7e, 0x2b, 0x8d, 0xe0, 0xe5, 0x82, 0xc8, 0x6b, 0x6b, 0x0d, 0x90, 0x7b, 0xb3, 0x60, 0xb9, 0x7f, 0x40, 0xab, 0x5d, 0x03, 0x8f, 0x6b, 0x75, 0xc8, 0x14, 0xb2, 0x7d, 0x9b, + 0x96, 0x8d, 0x41, 0x98, 0x32, 0xbc, 0x8c, 0x2b, 0xee, 0x60, 0x5e, 0xf6, 0xe5, 0x05, 0x9d, 0x33, 0x10, 0x0d, 0x90, 0x48, 0x5d, 0x37, 0x84, 0x50, 0x01, 0x42, 0x21, 0x73, 0x6c, 0x07, 0x40, 0x7c, + 0xac, 0x26, 0x04, 0x08, 0xaa, 0x64, 0x92, 0x66, 0x19, 0x78, 0x8b, 0x86, 0x01, 0xc2, 0xa7, 0x52, 0xd1, 0xa6, 0xcb, 0xf8, 0x20, 0xd7, 0xc7, 0xa0, 0x47, 0x16, 0x20, 0x32, 0x25, 0xb3, 0x89, 0x5b, + 0x93, 0x42, 0xd1, 0x47, 0xa8, 0x18, 0x5c, 0xfc, 0x1b, 0xb6, 0x5b, 0xa0, 0x6b, 0x41, 0x42, 0x33, 0x99, 0x03, 0xc0, 0xac, 0x46, 0x51, 0x38, 0x5b, 0x45, 0xd9, 0x8a, 0x8b, 0x19, 0xd2, 0x8c, 0xd6, + 0xba, 0xb0, 0x88, 0x78, 0x7f, 0x7e, 0xe1, 0xb1, 0x24, 0x61, 0x76, 0x6b, 0x43, 0xcb, 0xcc, 0xb9, 0x64, 0x34, 0x42, 0x7d, 0x93, 0xc0, 0x65, 0x55, 0x06, 0x88, 0xf6, 0x94, 0x8e, 0xd1, 0xb5, 0x47, + 0x5a, 0x42, 0x5f, 0x1b, 0x85, 0x20, 0x9d, 0x06, 0x1c, 0x08, 0xb5, 0x6c, 0x1c, 0xc0, 0x69, 0xf6, 0xc0, 0xa7, 0xc6, 0xf2, 0x93, 0x58, 0xca, 0xb9, 0x11, 0x08, 0x77, 0x32, 0xa6, 0x49, 0xd2, 0x7c, + 0x9b, 0x98, 0xf9, 0xa4, 0x88, 0x79, 0x38, 0x7d, 0x9b, 0x00, 0xc2, 0x59, 0x59, 0xa7, 0x16, 0x54, 0xd6, 0xf6, 0xa9, 0x46, 0x16, 0x45, 0x13, 0xe4, 0x7a, 0x75, 0xd0, 0x05, 0x98, 0x6c, 0x23, 0x63, + 0xc0, 0x9f, 0x6b, 0x53, 0x7e, 0xca, 0x78, 0xb9, 0x30, 0x3a, 0x5f, 0xa4, 0x57, 0x60, 0x8a, 0x58, 0x6a, 0x65, 0x3a, 0x34, 0x7d, 0xb0, 0x4d, 0xfc, 0xc1, 0x91, 0x75, 0xb3, 0xa3, 0x01, 0x17, 0x25, + 0x36, 0x06, 0x2a, 0x65, 0x8a, 0x95, 0x27, 0x75, 0x70, 0xc8, 0x85, 0x2c, 0xa8, 0x97, 0x3f, 0x4a, 0xe1, 0x23, 0xa3, 0x34, 0x04, 0x7d, 0xd7, 0x11, 0xc8, 0x92, 0x7a, 0x63, 0x4a, 0x03, 0x38, 0x8a, + 0x52, 0x7b, 0x03, 0x4b, 0xf7, 0xa8, 0x17, 0x0f, 0xa7, 0x02, 0xc1, 0xf7, 0xc2, 0x3e, 0xc3, 0x2d, 0x18, 0xa2, 0x37, 0x48, 0x90, 0xbe, 0x9c, 0x78, 0x7a, 0x94, 0x09, 0xc8, 0x2d, 0x19, 0x2c, 0x4b, + 0xb7, 0x05, 0xa2, 0xf9, 0x96, 0xce, 0x40, 0x5d, 0xa0, 0xb7, 0x1f, 0x67, 0xc6, 0xce, 0xc0, 0xd3, 0x56, 0x86, 0xd5, 0x13, 0x42, 0x34, 0x32, 0xe5, 0x12, 0xac, 0x40, 0x44, 0x55, 0x7e, 0x86, 0x8a, + 0x62, 0x48, 0x00, 0x10, 0x9a, 0x33, 0x55, 0xf9, 0x8f, 0x15, 0x14, 0x44, 0xe2, 0x85, 0x2e, 0x27, 0xea, 0x6e, 0xdb, 0x19, 0x92, 0xca, 0xd3, 0x97, 0x3c, 0x3a, 0x6f, 0xf7, 0x9a, 0x5a, 0x04, 0x9a, + 0x25, 0x9e, 0xb5, 0x41, 0x5a, 0xa2, 0xa2, 0x62, 0x45, 0x6e, 0xc9, 0x49, 0x5b, 0xbb, 0x52, 0x00, 0xd8, 0xd3, 0x16, 0x3a, 0x5b, 0x10, 0x22, 0x62, 0x92, 0xec, 0xa0, 0x10, 0x21, 0x38, 0x9d, 0xa3, + 0x78, 0x81, 0xe2, 0x76, 0x30, 0x65, 0x50, 0xc6, 0xef, 0xb6, 0x44, 0x0e, 0xc5, 0x1a, 0x2f, 0x73, 0x48, 0x34, 0x9b, 0x85, 0x1c, 0xd4, 0xaa, 0x01, 0x75, 0xa0, 0x55, 0x02, 0x13, 0xc4, 0x79, 0x1d, + 0x91, 0x01, 0x12, 0x20, 0x82, 0x4b, 0x2b, 0x61, 0x65, 0x08, 0x13, 0xad, 0xfd, 0x2c, 0xb1, 0x05, 0x38, 0xbf, 0xab, 0x0a, 0x72, 0x6f, 0x81, 0x12, 0x9e, 0xd2, 0xc0, 0xf0, 0x6a, 0x16, 0xb7, 0x01, + 0x09, 0x0b, 0xf0, 0x48, 0xc5, 0xa4, 0x01, 0x26, 0xd5, 0x72, 0xfc, 0xd4, 0x7a, 0xa1, 0x21, 0x8f, 0xb0, 0x15, 0x47, 0xd1, 0x50, 0x79, 0x2d, 0x23, 0x16, 0xcb, 0x32, 0x0d, 0x51, 0x44, 0xba, 0x35, + 0x08, 0xa1, 0xeb, 0xbb, 0x5a, 0xc1, 0xc2, 0x29, 0x13, 0xe8, 0x29, 0x5f, 0xab, 0x59, 0xbf, 0x58, 0x37, 0xa7, 0x78, 0xcf, 0x28, 0x22, 0x7e, 0x07, 0xe1, 0x03, 0x2d, 0xab, 0x7d, 0x0e, 0x09, 0xa1, + 0x5f, 0x13, 0x41, 0x48, 0xc1, 0x20, 0x09, 0xda, 0x53, 0x6b, 0x22, 0xcc, 0x62, 0x47, 0x4e, 0x69, 0xcc, 0x15, 0x54, 0xc0, 0x81, 0x4d, 0x6c, 0xa0, 0xb7, 0x22, 0x59, 0x43, 0x83, 0xa9, 0xd0, 0xa2, + 0xc7, 0x7f, 0xd3, 0x65, 0xa5, 0x54, 0x42, 0x95, 0xfb, 0xb9, 0x73, 0xf9, 0x1e, 0xa5, 0x64, 0x90, 0xd6, 0xca, 0x68, 0x76, 0x49, 0x7b, 0x98, 0xb3, 0xcb, 0x12, 0x41, 0x7c, 0x25, 0x7b, 0x6d, 0x0f, + 0x71, 0x83, 0xdb, 0xb6, 0x9e, 0x33, 0x07, 0x5b, 0xeb, 0x01, 0x17, 0xb6, 0x91, 0x4c, 0x69, 0xba, 0x38, 0x34, 0x94, 0x22, 0xf2, 0xf4, 0x33, 0x64, 0x82, 0x2a, 0x25, 0x70, 0x95, 0x2d, 0xd5, 0x07, + 0x7b, 0x90, 0x75, 0x5f, 0x15, 0x74, 0x11, 0x5b, 0x8e, 0x22, 0x14, 0x27, 0x58, 0x59, 0x61, 0x91, 0x3a, 0x9b, 0xfa, 0x05, 0x02, 0xb5, 0xd7, 0x9a, 0xb7, 0x81, 0x17, 0x44, 0xe6, 0x56, 0x3c, 0x5b, + 0x62, 0xc5, 0xcc, 0x4e, 0x93, 0x23, 0x9a, 0x0a, 0x8c, 0xc6, 0x0f, 0xe8, 0x48, 0xf8, 0x4a, 0x95, 0xf5, 0x90, 0x25, 0x99, 0xb5, 0x4a, 0x06, 0x62, 0x93, 0xa2, 0x02, 0x1d, 0xa1, 0x96, 0x76, 0x6c, + 0x17, 0xc7, 0xe8, 0x63, 0xaf, 0x79, 0x0c, 0x27, 0x0b, 0x21, 0x6a, 0x25, 0x13, 0x8d, 0xda, 0x0c, 0x81, 0x26, 0xe0, 0x93, 0x77, 0x87, 0x98, 0x59, 0xdb, 0x35, 0x8f, 0x9b, 0x82, 0xb7, 0xc8, 0xa6, + 0x79, 0x2a, 0xce, 0xe9, 0x2a, 0x4c, 0xbd, 0xe3, 0xce, 0xdd, 0x45, 0x00, 0xac, 0xbc, 0x55, 0x5c, 0x28, 0x8e, 0xff, 0x97, 0x95, 0x26, 0x5b, 0x90, 0x05, 0x35, 0x1c, 0x52, 0xe2, 0x65, 0x35, 0x54, + 0xab, 0xaa, 0xf8, 0x72, 0xdf, 0x95, 0xca, 0x7f, 0x79, 0x59, 0x03, 0xf0, 0xb0, 0xa1, 0x82, 0xb1, 0x8a, 0xeb, 0x04, 0x75, 0xb2, 0x9f, 0x6e, 0x3a, 0xbf, 0x4c, 0x22, 0x50, 0xfe, 0x7b, 0x84, 0x2a, + 0x73, 0x65, 0x50, 0x16, 0xa8, 0xfc, 0x72, 0x9f, 0x39, 0x05, 0x07, 0xac, 0xa9, 0x36, 0x82, 0x5a, 0x98, 0xb3, 0xa3, 0x2e, 0x6b, 0x25, 0x54, 0xce, 0x95, 0x28, 0x94, 0x1a, 0x3b, 0xb8, 0xc9, 0x09, + 0x96, 0x00, 0x8d, 0x74, 0xfb, 0xcd, 0x02, 0x0a, 0x02, 0xe7, 0x06, 0xa6, 0xde, 0x7b, 0x02, 0xaf, 0x40, 0x4c, 0x10, 0xdb, 0x00, 0xfa, 0xec, 0x02, 0xd3, 0xea, 0xa6, 0xd9, 0x56, 0x1a, 0x15, 0x65, + 0xa7, 0xb0, 0x5c, 0x63, 0x66, 0xd0, 0x9d, 0xa7, 0xa5, 0x37, 0xf2, 0x0c, 0x7b, 0x28, 0x59, 0xa8, 0x3e, 0x02, 0x9e, 0x13, 0xa9, 0xbd, 0x28, 0x91, 0x57, 0xc5, 0xb7, 0x4c, 0x84, 0xea, 0xa3, 0x07, + 0x75, 0x3d, 0x43, 0x12, 0x02, 0xa3, 0xd9, 0xb6, 0x16, 0x22, 0x18, 0xbe, 0xc5, 0x34, 0x69, 0x45, 0xbf, 0xef, 0x55, 0xb6, 0x24, 0xc5, 0xc6, 0xe3, 0x73, 0x35, 0x9b, 0xb1, 0xc4, 0x79, 0x95, 0x2b, + 0xba, 0xba, 0x4d, 0x65, 0x55, 0xc2, 0x76, 0x57, 0x3e, 0x51, 0x52, 0xb5, 0x53, 0x90, 0x19, 0x99, 0xf6, 0x94, 0x02, 0xd1, 0x50, 0xbe, 0xf7, 0x9d, 0x74, 0xfb, 0x29, 0x53, 0x01, 0x8f, 0xf4, 0x86, + 0x66, 0x74, 0x6a, 0xce, 0x60, 0x78, 0x14, 0xa1, 0xfa, 0x33, 0x19, 0x57, 0x20, 0xf8, 0x38, 0x78, 0xd3, 0xb5, 0x75, 0xc7, 0x25, 0x74, 0x4a, 0x72, 0x07, 0x0d, 0xd0, 0x44, 0x01, 0x80, 0x42, 0xda, + 0x25, 0x71, 0x4d, 0x17, 0x30, 0x90, 0x32, 0x3a, 0x51, 0xe6, 0xc0, 0x63, 0xd2, 0x03, 0x88, 0x13, 0x80, 0x91, 0x27, 0x61, 0xfc, 0x34, 0x10, 0x83, 0x90, 0x95, 0xf2, 0x6c, 0x0e, 0x68, 0x7a, 0x00, + 0x70, 0x54, 0x95, 0xe1, 0x71, 0xb5, 0x71, 0x51, 0xac, 0xe0, 0x49, 0x8e, 0x30, 0xf1, 0x4c, 0xa9, 0xb0, 0x2f, 0x6e, 0x40, 0x83, 0x18, 0x54, 0xc2, 0xe0, 0xab, 0x1e, 0xcd, 0x0c, 0x21, 0xd8, 0xe4, + 0xc7, 0xe6, 0x69, 0xcd, 0x72, 0x82, 0x30, 0xb9, 0xd1, 0x1f, 0x72, 0xc2, 0x66, 0xe3, 0x44, 0x66, 0xf9, 0xc0, 0x15, 0x9e, 0xf4, 0x24, 0xf8, 0xf3, 0x1d, 0x95, 0xa5, 0x7b, 0xa0, 0xe2, 0x10, 0x54, + 0x3c, 0x10, 0xc6, 0x50, 0x3f, 0xb5, 0xc6, 0x3e, 0xd2, 0x3a, 0xa3, 0x6c, 0xd6, 0xa6, 0xf3, 0x78, 0x26, 0x1b, 0x0b, 0x1e, 0x79, 0x50, 0x9d, 0x8b, 0xeb, 0x36, 0xaa, 0x26, 0x3d, 0xc9, 0x15, 0x45, + 0xe5, 0x33, 0x69, 0xdf, 0x26, 0x83, 0x7f, 0x39, 0x4c, 0x56, 0x77, 0x7c, 0x95, 0xb6, 0x48, 0xbd, 0x1a, 0x72, 0x92, 0x1a, 0xbf, 0x49, 0x56, 0x3f, 0x99, 0xcb, 0x9d, 0x98, 0xea, 0xb5, 0xc6, 0x66, + 0x66, 0xf6, 0xb1, 0x6f, 0x74, 0x02, 0x24, 0x81, 0xfa, 0x21, 0x4e, 0x61, 0x76, 0x98, 0xd3, 0xbb, 0xd1, 0x3c, 0xb3, 0x08, 0x71, 0x3f, 0xdc, 0xc7, 0xcf, 0xd3, 0x97, 0xb9, 0xca, 0x39, 0xaf, 0xf4, + 0xc7, 0x44, 0xd5, 0x71, 0x5d, 0x58, 0x96, 0x6f, 0x2c, 0xf9, 0x70, 0x70, 0x15, 0xc8, 0xf3, 0x54, 0x3e, 0xd2, 0x86, 0xa3, 0xd8, 0xd5, 0xcb, 0xf6, 0x4a, 0xce, 0xdf, 0xc0, 0x29, 0x71, 0xa9, 0x10, + 0x72, 0xc6, 0x9d, 0x2e, 0xf4, 0x98, 0x29, 0xf1, 0x03, 0x7f, 0x05, 0x0c, 0x5b, 0x92, 0x22, 0x98, 0x56, 0xcb, 0x12, 0xb4, 0x56, 0xcc, 0x09, 0x52, 0x82, 0xa6, 0x26, 0x87, 0xea, 0x38, 0xc9, 0x77, + 0x8a, 0xea, 0x49, 0x1d, 0xff, 0x06, 0x97, 0x11, 0xfb, 0xbe, 0x05, 0xe8, 0xcd, 0x9b, 0xf4, 0x4a, 0x8e, 0x71, 0x26, 0x19, 0x57, 0x3e, 0x12, 0xea, 0xa7, 0xb2, 0x38, 0x29, 0xdc, 0x67, 0x26, 0xbf, + 0xe3, 0x3d, 0xa1, 0x36, 0xb8, 0x1e, 0x15, 0x32, 0x51, 0x50, 0x8f, 0x62, 0x85, 0xba, 0x15, 0xb2, 0xc1, 0x23, 0x76, 0x77, 0xfe, 0x5b, 0x14, 0xb4, 0xe3, 0x3f, 0x98, 0xc3, 0x26, 0xbc, 0x58, 0xb9, + 0xd8, 0xe0, 0x75, 0xa2, 0x5b, 0x94, 0xc8, 0xa2, 0x32, 0x33, 0x02, 0x9d, 0xcc, 0x78, 0x6b, 0x13, 0x5c, 0x56, 0x16, 0x4b, 0xa3, 0xd1, 0x60, 0xcb, 0xce, 0xa8, 0x54, 0xb7, 0x97, 0x1f, 0x9c, 0xd7, + 0x3a, 0x38, 0x3a, 0xac, 0x05, 0x0a, 0x30, 0x2a, 0xd8, 0x3b, 0x3e, 0x3a, 0xb9, 0x02, 0x46, 0xad, 0x16, 0x0a, 0x32, 0x1d, 0x33, 0x0a, 0xcd, 0xec, 0x7c, 0xa6, 0x64, 0x3d, 0x7e, 0xc0, 0x1f, 0x91, + 0x69, 0x1f, 0x16, 0x32, 0x5b, 0xdf, 0x39, 0x69, 0x50, 0xb8, 0x8d, 0xaf, 0xe3, 0x69, 0xc6, 0x54, 0xb8, 0x52, 0x05, 0x5c, 0x97, 0x03, 0x62, 0xc6, 0x13, 0x80, 0x46, 0x07, 0x57, 0xc6, 0x58, 0x90, + 0xf4, 0xe5, 0x92, 0x22, 0xe4, 0xa4, 0x06, 0x0b, 0x26, 0xc0, 0xeb, 0xc1, 0x01, 0x97, 0x59, 0x0d, 0xe3, 0xc8, 0xf0, 0x95, 0x5d, 0x65, 0x4b, 0x37, 0x1c, 0xcb, 0x90, 0xac, 0xa3, 0x71, 0xb2, 0x94, + 0x47, 0x6c, 0x16, 0xa4, 0x59, 0x6a, 0x1d, 0xe8, 0x30, 0x9e, 0x2a, 0x36, 0x12, 0xc6, 0x9b, 0x71, 0x25, 0x31, 0x05, 0x01, 0xe0, 0xc0, 0x49, 0xb8, 0x74, 0x40, 0xd9, 0xa6, 0xd0, 0xec, 0xb9, 0x99, + 0xc9, 0xa0, 0x94, 0x2a, 0xa3, 0x40, 0xf6, 0x03, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, + 0x54, 0xa3, 0x16, 0x65, 0x29, 0xb5, 0x39, 0x22, 0xde, 0xe4, 0xab, 0xa0, 0x00, 0x38, 0x95, 0x81, 0x71, 0x7d, 0x36, 0xf5, 0x6f, 0x39, 0xaf, 0x73, 0x00, 0xb3, 0x1d, 0x83, 0x1a, 0x4d, 0x8c, 0x97, + 0x61, 0x28, 0xe0, 0x9d, 0xed, 0xe7, 0x1a, 0x5a, 0x86, 0x26, 0xed, 0x79, 0xd4, 0x51, 0x14, 0x08, 0x00, 0xe0, 0x3b, 0x59, 0xb9, 0x56, 0xf8, 0x21, 0x0e, 0x55, 0x60, 0x67, 0x40, 0x7d, 0x13, 0xdc, + 0x90, 0xfa, 0x9e, 0x8b, 0x87, 0x2b, 0xfb, 0x8f, 0xa0, 0x82, 0x04, 0xe5, 0x03, 0x82, 0x04, 0xe1, 0x00, 0xa0, 0xb7, 0x1f, 0x67, 0xc6, 0xce, 0xc0, 0xd3, 0x56, 0x86, 0xd5, 0x13, 0x42, 0x34, 0x32, + 0xe5, 0x12, 0xac, 0x40, 0x44, 0x55, 0x7e, 0x86, 0x8a, 0x62, 0x48, 0x00, 0x10, 0x9a, 0x33, 0x55, 0xf9, 0x8f, 0x15, 0x14, 0x44, 0xe2, 0x85, 0x2e, 0x27, 0xea, 0x6e, 0xdb, 0x19, 0x92, 0xca, 0xd3, + 0x97, 0x3c, 0x3a, 0x6f, 0xf7, 0x9a, 0x5a, 0x04, 0x9a, 0x25, 0x9e, 0xb5, 0x41, 0x5a, 0xa2, 0xa2, 0x62, 0x45, 0x6e, 0xc9, 0x49, 0x5b, 0xbb, 0x52, 0x00, 0xd8, 0xd3, 0x16, 0x3a, 0x5b, 0x10, 0x22, + 0x62, 0x92, 0xec, 0xa0, 0x10, 0x21, 0x38, 0x9d, 0xa3, 0x78, 0x81, 0xe2, 0x76, 0x30, 0x65, 0x50, 0xc6, 0xef, 0xb6, 0x44, 0x0e, 0xc5, 0x1a, 0x2f, 0x73, 0x48, 0x34, 0x9b, 0x85, 0x1c, 0xd4, 0xaa, + 0x01, 0x75, 0xa0, 0x55, 0x02, 0x13, 0xc4, 0x79, 0x1d, 0x91, 0x01, 0x12, 0x20, 0x82, 0x4b, 0x2b, 0x61, 0x65, 0x08, 0x13, 0xad, 0xfd, 0x2c, 0xb1, 0x05, 0x38, 0xbf, 0xab, 0x0a, 0x72, 0x6f, 0x81, + 0x12, 0x9e, 0xd2, 0xc0, 0xf0, 0x6a, 0x16, 0xb7, 0x01, 0x09, 0x0b, 0xf0, 0x48, 0xc5, 0xa4, 0x01, 0x26, 0xd5, 0x72, 0xfc, 0xd4, 0x7a, 0xa1, 0x21, 0x8f, 0xb0, 0x15, 0x47, 0xd1, 0x50, 0x79, 0x2d, + 0x23, 0x16, 0xcb, 0x32, 0x0d, 0x51, 0x44, 0xba, 0x35, 0x08, 0xa1, 0xeb, 0xbb, 0x5a, 0xc1, 0xc2, 0x29, 0x13, 0xe8, 0x29, 0x5f, 0xab, 0x59, 0xbf, 0x58, 0x37, 0xa7, 0x78, 0xcf, 0x28, 0x22, 0x7e, + 0x07, 0xe1, 0x03, 0x2d, 0xab, 0x7d, 0x0e, 0x09, 0xa1, 0x5f, 0x13, 0x41, 0x48, 0xc1, 0x20, 0x09, 0xda, 0x53, 0x6b, 0x22, 0xcc, 0x62, 0x47, 0x4e, 0x69, 0xcc, 0x15, 0x54, 0xc0, 0x81, 0x4d, 0x6c, + 0xa0, 0xb7, 0x22, 0x59, 0x43, 0x83, 0xa9, 0xd0, 0xa2, 0xc7, 0x7f, 0xd3, 0x65, 0xa5, 0x54, 0x42, 0x95, 0xfb, 0xb9, 0x73, 0xf9, 0x1e, 0xa5, 0x64, 0x90, 0xd6, 0xca, 0x68, 0x76, 0x49, 0x7b, 0x98, + 0xb3, 0xcb, 0x12, 0x41, 0x7c, 0x25, 0x7b, 0x6d, 0x0f, 0x71, 0x83, 0xdb, 0xb6, 0x9e, 0x33, 0x07, 0x5b, 0xeb, 0x01, 0x17, 0xb6, 0x91, 0x4c, 0x69, 0xba, 0x38, 0x34, 0x94, 0x22, 0xf2, 0xf4, 0x33, + 0x64, 0x82, 0x2a, 0x25, 0x70, 0x95, 0x2d, 0xd5, 0x07, 0x7b, 0x90, 0x75, 0x5f, 0x15, 0x74, 0x11, 0x5b, 0x8e, 0x22, 0x14, 0x27, 0x58, 0x59, 0x61, 0x91, 0x3a, 0x9b, 0xfa, 0x05, 0x02, 0xb5, 0xd7, + 0x9a, 0xb7, 0x81, 0x17, 0x44, 0xe6, 0x56, 0x3c, 0x5b, 0x62, 0xc5, 0xcc, 0x4e, 0x93, 0x23, 0x9a, 0x0a, 0x8c, 0xc6, 0x0f, 0xe8, 0x48, 0xf8, 0x4a, 0x95, 0xf5, 0x90, 0x25, 0x99, 0xb5, 0x4a, 0x06, + 0x62, 0x93, 0xa2, 0x02, 0x1d, 0xa1, 0x96, 0x76, 0x6c, 0x17, 0xc7, 0xe8, 0x63, 0xaf, 0x79, 0x0c, 0x27, 0x0b, 0x21, 0x6a, 0x25, 0x13, 0x8d, 0xda, 0x0c, 0x81, 0x26, 0xe0, 0x93, 0x77, 0x87, 0x98, + 0x59, 0xdb, 0x35, 0x8f, 0x9b, 0x82, 0xb7, 0xc8, 0xa6, 0x79, 0x2a, 0xce, 0xe9, 0x2a, 0x4c, 0xbd, 0xe3, 0xce, 0xdd, 0x45, 0x00, 0xac, 0xbc, 0x55, 0x5c, 0x28, 0x8e, 0xff, 0x97, 0x95, 0x26, 0x5b, + 0x90, 0x05, 0x35, 0x1c, 0x52, 0xe2, 0x65, 0x35, 0x54, 0xab, 0xaa, 0xf8, 0x72, 0xdf, 0x95, 0xca, 0x7f, 0x79, 0x59, 0x03, 0xf0, 0xb0, 0xa1, 0x82, 0xb1, 0x8a, 0xeb, 0x04, 0x75, 0xb2, 0x9f, 0x6e, + 0x3a, 0xbf, 0x4c, 0x22, 0x50, 0xfe, 0x7b, 0x84, 0x2a, 0x73, 0x65, 0x50, 0x16, 0xa8, 0xfc, 0x72, 0x9f, 0x39, 0x05, 0x07, 0xac, 0xa9, 0x36, 0x82, 0x5a, 0x98, 0xb3, 0xa3, 0x2e, 0x6b, 0x25, 0x54, + 0xce, 0x95, 0x28, 0x94, 0x1a, 0x3b, 0xb8, 0xc9, 0x09, 0x96, 0x00, 0x8d, 0x74, 0xfb, 0xcd, 0x02, 0x0a, 0x02, 0xe7, 0x06, 0xa6, 0xde, 0x7b, 0x02, 0xaf, 0x40, 0x4c, 0x10, 0xdb, 0x00, 0xfa, 0xec, + 0x02, 0xd3, 0xea, 0xa6, 0xd9, 0x56, 0x1a, 0x15, 0x65, 0xa7, 0xb0, 0x5c, 0x63, 0x66, 0xd0, 0x9d, 0xa7, 0xa5, 0x37, 0xf2, 0x0c, 0x7b, 0x28, 0x59, 0xa8, 0x3e, 0x02, 0x9e, 0x13, 0xa9, 0xbd, 0x28, + 0x91, 0x57, 0xc5, 0xb7, 0x4c, 0x84, 0xea, 0xa3, 0x07, 0x75, 0x3d, 0x43, 0x12, 0x02, 0xa3, 0xd9, 0xb6, 0x16, 0x22, 0x18, 0xbe, 0xc5, 0x34, 0x69, 0x45, 0xbf, 0xef, 0x55, 0xb6, 0x24, 0xc5, 0xc6, + 0xe3, 0x73, 0x35, 0x9b, 0xb1, 0xc4, 0x79, 0x95, 0x2b, 0xba, 0xba, 0x4d, 0x65, 0x55, 0xc2, 0x76, 0x57, 0x3e, 0x51, 0x52, 0xb5, 0x53, 0x90, 0x19, 0x99, 0xf6, 0x94, 0x02, 0xd1, 0x50, 0xbe, 0xf7, + 0x9d, 0x74, 0xfb, 0x29, 0x53, 0x01, 0x8f, 0xf4, 0x86, 0x66, 0x74, 0x6a, 0xce, 0x60, 0x78, 0x14, 0xa1, 0xfa, 0x33, 0x19, 0x57, 0x20, 0xf8, 0x38, 0x78, 0xd3, 0xb5, 0x75, 0xc7, 0x25, 0x74, 0x4a, + 0x72, 0x07, 0x0d, 0xd0, 0x44, 0x01, 0x80, 0x42, 0xda, 0x25, 0x71, 0x4d, 0x17, 0x30, 0x90, 0x32, 0x3a, 0x51, 0xe6, 0xc0, 0x63, 0xd2, 0x03, 0x88, 0x13, 0x80, 0x91, 0x27, 0x61, 0xfc, 0x34, 0x10, + 0x83, 0x90, 0x95, 0xf2, 0x6c, 0x0e, 0x68, 0x7a, 0x00, 0x70, 0x54, 0x95, 0xe1, 0x71, 0xb5, 0x71, 0x51, 0xac, 0xe0, 0x49, 0x8e, 0x30, 0xf1, 0x4c, 0xa9, 0xb0, 0x2f, 0x6e, 0x40, 0x83, 0x18, 0x54, + 0xc2, 0xe0, 0xab, 0x1e, 0xcd, 0x0c, 0x21, 0xd8, 0xe4, 0xc7, 0xe6, 0x69, 0xcd, 0x72, 0x82, 0x30, 0xb9, 0xd1, 0x1f, 0x72, 0xc2, 0x66, 0xe3, 0x44, 0x66, 0xf9, 0xc0, 0x15, 0x9e, 0xf4, 0x24, 0xf8, + 0xf3, 0x1d, 0x95, 0xa5, 0x7b, 0xa0, 0xe2, 0x10, 0x54, 0x3c, 0x10, 0xc6, 0x50, 0x3f, 0xb5, 0xc6, 0x3e, 0xd2, 0x3a, 0xa3, 0x6c, 0xd6, 0xa6, 0xf3, 0x78, 0x26, 0x1b, 0x0b, 0x1e, 0x79, 0x50, 0x9d, + 0x8b, 0xeb, 0x36, 0xaa, 0x26, 0x3d, 0xc9, 0x15, 0x45, 0xe5, 0x33, 0x69, 0xdf, 0x26, 0x83, 0x7f, 0x39, 0x4c, 0x56, 0x77, 0x7c, 0x95, 0xb6, 0x48, 0xbd, 0x1a, 0x72, 0x92, 0x1a, 0xbf, 0x49, 0x56, + 0x3f, 0x99, 0xcb, 0x9d, 0x98, 0xea, 0xb5, 0xc6, 0x66, 0x66, 0xf6, 0xb1, 0x6f, 0x74, 0x02, 0x24, 0x81, 0xfa, 0x21, 0x4e, 0x61, 0x76, 0x98, 0xd3, 0xbb, 0xd1, 0x3c, 0xb3, 0x08, 0x71, 0x3f, 0xdc, + 0xc7, 0xcf, 0xd3, 0x97, 0xb9, 0xca, 0x39, 0xaf, 0xf4, 0xc7, 0x44, 0xd5, 0x71, 0x5d, 0x58, 0x96, 0x6f, 0x2c, 0xf9, 0x70, 0x70, 0x15, 0xc8, 0xf3, 0x54, 0x3e, 0xd2, 0x86, 0xa3, 0xd8, 0xd5, 0xcb, + 0xf6, 0x4a, 0xce, 0xdf, 0xc0, 0x29, 0x71, 0xa9, 0x10, 0x72, 0xc6, 0x9d, 0x2e, 0xf4, 0x98, 0x29, 0xf1, 0x03, 0x7f, 0x05, 0x0c, 0x5b, 0x92, 0x22, 0x98, 0x56, 0xcb, 0x12, 0xb4, 0x56, 0xcc, 0x09, + 0x52, 0x82, 0xa6, 0x26, 0x87, 0xea, 0x38, 0xc9, 0x77, 0x8a, 0xea, 0x49, 0x1d, 0xff, 0x06, 0x97, 0x11, 0xfb, 0xbe, 0x05, 0xe8, 0xcd, 0x9b, 0xf4, 0x4a, 0x8e, 0x71, 0x26, 0x19, 0x57, 0x3e, 0x12, + 0xea, 0xa7, 0xb2, 0x38, 0x29, 0xdc, 0x67, 0x26, 0xbf, 0xe3, 0x3d, 0xa1, 0x36, 0xb8, 0x1e, 0x15, 0x32, 0x51, 0x50, 0x8f, 0x62, 0x85, 0xba, 0x15, 0xb2, 0xc1, 0x23, 0x76, 0x77, 0xfe, 0x5b, 0x14, + 0xb4, 0xe3, 0x3f, 0x98, 0xc3, 0x26, 0xbc, 0x58, 0xb9, 0xd8, 0xe0, 0x75, 0xa2, 0x5b, 0x94, 0xc8, 0xa2, 0x32, 0x33, 0x02, 0x9d, 0xcc, 0x78, 0x6b, 0x13, 0x5c, 0x56, 0x16, 0x4b, 0xa3, 0xd1, 0x60, + 0xcb, 0xce, 0xa8, 0x54, 0xb7, 0x97, 0x1f, 0x9c, 0xd7, 0x3a, 0x38, 0x3a, 0xac, 0x05, 0x0a, 0x30, 0x2a, 0xd8, 0x3b, 0x3e, 0x3a, 0xb9, 0x02, 0x46, 0xad, 0x16, 0x0a, 0x32, 0x1d, 0x33, 0x0a, 0xcd, + 0xec, 0x7c, 0xa6, 0x64, 0x3d, 0x7e, 0xc0, 0x1f, 0x91, 0x69, 0x1f, 0x16, 0x32, 0x5b, 0xdf, 0x39, 0x69, 0x50, 0xb8, 0x8d, 0xaf, 0xe3, 0x69, 0xc6, 0x54, 0xb8, 0x52, 0x05, 0x5c, 0x97, 0x03, 0x62, + 0xc6, 0x13, 0x80, 0x46, 0x07, 0x57, 0xc6, 0x58, 0x90, 0xf4, 0xe5, 0x92, 0x22, 0xe4, 0xa4, 0x06, 0x0b, 0x26, 0xc0, 0xeb, 0xc1, 0x01, 0x97, 0x59, 0x0d, 0xe3, 0xc8, 0xf0, 0x95, 0x5d, 0x65, 0x4b, + 0x37, 0x1c, 0xcb, 0x90, 0xac, 0xa3, 0x71, 0xb2, 0x94, 0x47, 0x6c, 0x16, 0xa4, 0x59, 0x6a, 0x1d, 0xe8, 0x30, 0x9e, 0x2a, 0x36, 0x12, 0xc6, 0x9b, 0x71, 0x25, 0x31, 0x05, 0x01, 0xe0, 0xc0, 0x49, + 0xb8, 0x74, 0x40, 0xd9, 0xa6, 0xd0, 0xec, 0xb9, 0x99, 0xc9, 0xa0, 0x94, 0x2a, 0xa3, 0x40, 0xf6, 0x03, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, + 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, 0x54, 0xa3, 0x16, 0x65, 0x29, 0xb5, 0x39, 0x22, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + }, + .spki_len = 1219, + .spki = { + 0x30, 0x82, 0x04, 0xbf, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x05, 0x03, 0x03, 0x05, 0x00, 0x03, 0x82, 0x04, 0xaa, 0x00, 0x30, 0x82, 0x04, 0xa5, 0x03, 0x82, + 0x04, 0xa1, 0x00, 0xa0, 0xb7, 0x1f, 0x67, 0xc6, 0xce, 0xc0, 0xd3, 0x56, 0x86, 0xd5, 0x13, 0x42, 0x34, 0x32, 0xe5, 0x12, 0xac, 0x40, 0x44, 0x55, 0x7e, 0x86, 0x8a, 0x62, 0x48, 0x00, 0x10, 0x9a, + 0x33, 0x55, 0xf9, 0x8f, 0x15, 0x14, 0x44, 0xe2, 0x85, 0x2e, 0x27, 0xea, 0x6e, 0xdb, 0x19, 0x92, 0xca, 0xd3, 0x97, 0x3c, 0x3a, 0x6f, 0xf7, 0x9a, 0x5a, 0x04, 0x9a, 0x25, 0x9e, 0xb5, 0x41, 0x5a, + 0xa2, 0xa2, 0x62, 0x45, 0x6e, 0xc9, 0x49, 0x5b, 0xbb, 0x52, 0x00, 0xd8, 0xd3, 0x16, 0x3a, 0x5b, 0x10, 0x22, 0x62, 0x92, 0xec, 0xa0, 0x10, 0x21, 0x38, 0x9d, 0xa3, 0x78, 0x81, 0xe2, 0x76, 0x30, + 0x65, 0x50, 0xc6, 0xef, 0xb6, 0x44, 0x0e, 0xc5, 0x1a, 0x2f, 0x73, 0x48, 0x34, 0x9b, 0x85, 0x1c, 0xd4, 0xaa, 0x01, 0x75, 0xa0, 0x55, 0x02, 0x13, 0xc4, 0x79, 0x1d, 0x91, 0x01, 0x12, 0x20, 0x82, + 0x4b, 0x2b, 0x61, 0x65, 0x08, 0x13, 0xad, 0xfd, 0x2c, 0xb1, 0x05, 0x38, 0xbf, 0xab, 0x0a, 0x72, 0x6f, 0x81, 0x12, 0x9e, 0xd2, 0xc0, 0xf0, 0x6a, 0x16, 0xb7, 0x01, 0x09, 0x0b, 0xf0, 0x48, 0xc5, + 0xa4, 0x01, 0x26, 0xd5, 0x72, 0xfc, 0xd4, 0x7a, 0xa1, 0x21, 0x8f, 0xb0, 0x15, 0x47, 0xd1, 0x50, 0x79, 0x2d, 0x23, 0x16, 0xcb, 0x32, 0x0d, 0x51, 0x44, 0xba, 0x35, 0x08, 0xa1, 0xeb, 0xbb, 0x5a, + 0xc1, 0xc2, 0x29, 0x13, 0xe8, 0x29, 0x5f, 0xab, 0x59, 0xbf, 0x58, 0x37, 0xa7, 0x78, 0xcf, 0x28, 0x22, 0x7e, 0x07, 0xe1, 0x03, 0x2d, 0xab, 0x7d, 0x0e, 0x09, 0xa1, 0x5f, 0x13, 0x41, 0x48, 0xc1, + 0x20, 0x09, 0xda, 0x53, 0x6b, 0x22, 0xcc, 0x62, 0x47, 0x4e, 0x69, 0xcc, 0x15, 0x54, 0xc0, 0x81, 0x4d, 0x6c, 0xa0, 0xb7, 0x22, 0x59, 0x43, 0x83, 0xa9, 0xd0, 0xa2, 0xc7, 0x7f, 0xd3, 0x65, 0xa5, + 0x54, 0x42, 0x95, 0xfb, 0xb9, 0x73, 0xf9, 0x1e, 0xa5, 0x64, 0x90, 0xd6, 0xca, 0x68, 0x76, 0x49, 0x7b, 0x98, 0xb3, 0xcb, 0x12, 0x41, 0x7c, 0x25, 0x7b, 0x6d, 0x0f, 0x71, 0x83, 0xdb, 0xb6, 0x9e, + 0x33, 0x07, 0x5b, 0xeb, 0x01, 0x17, 0xb6, 0x91, 0x4c, 0x69, 0xba, 0x38, 0x34, 0x94, 0x22, 0xf2, 0xf4, 0x33, 0x64, 0x82, 0x2a, 0x25, 0x70, 0x95, 0x2d, 0xd5, 0x07, 0x7b, 0x90, 0x75, 0x5f, 0x15, + 0x74, 0x11, 0x5b, 0x8e, 0x22, 0x14, 0x27, 0x58, 0x59, 0x61, 0x91, 0x3a, 0x9b, 0xfa, 0x05, 0x02, 0xb5, 0xd7, 0x9a, 0xb7, 0x81, 0x17, 0x44, 0xe6, 0x56, 0x3c, 0x5b, 0x62, 0xc5, 0xcc, 0x4e, 0x93, + 0x23, 0x9a, 0x0a, 0x8c, 0xc6, 0x0f, 0xe8, 0x48, 0xf8, 0x4a, 0x95, 0xf5, 0x90, 0x25, 0x99, 0xb5, 0x4a, 0x06, 0x62, 0x93, 0xa2, 0x02, 0x1d, 0xa1, 0x96, 0x76, 0x6c, 0x17, 0xc7, 0xe8, 0x63, 0xaf, + 0x79, 0x0c, 0x27, 0x0b, 0x21, 0x6a, 0x25, 0x13, 0x8d, 0xda, 0x0c, 0x81, 0x26, 0xe0, 0x93, 0x77, 0x87, 0x98, 0x59, 0xdb, 0x35, 0x8f, 0x9b, 0x82, 0xb7, 0xc8, 0xa6, 0x79, 0x2a, 0xce, 0xe9, 0x2a, + 0x4c, 0xbd, 0xe3, 0xce, 0xdd, 0x45, 0x00, 0xac, 0xbc, 0x55, 0x5c, 0x28, 0x8e, 0xff, 0x97, 0x95, 0x26, 0x5b, 0x90, 0x05, 0x35, 0x1c, 0x52, 0xe2, 0x65, 0x35, 0x54, 0xab, 0xaa, 0xf8, 0x72, 0xdf, + 0x95, 0xca, 0x7f, 0x79, 0x59, 0x03, 0xf0, 0xb0, 0xa1, 0x82, 0xb1, 0x8a, 0xeb, 0x04, 0x75, 0xb2, 0x9f, 0x6e, 0x3a, 0xbf, 0x4c, 0x22, 0x50, 0xfe, 0x7b, 0x84, 0x2a, 0x73, 0x65, 0x50, 0x16, 0xa8, + 0xfc, 0x72, 0x9f, 0x39, 0x05, 0x07, 0xac, 0xa9, 0x36, 0x82, 0x5a, 0x98, 0xb3, 0xa3, 0x2e, 0x6b, 0x25, 0x54, 0xce, 0x95, 0x28, 0x94, 0x1a, 0x3b, 0xb8, 0xc9, 0x09, 0x96, 0x00, 0x8d, 0x74, 0xfb, + 0xcd, 0x02, 0x0a, 0x02, 0xe7, 0x06, 0xa6, 0xde, 0x7b, 0x02, 0xaf, 0x40, 0x4c, 0x10, 0xdb, 0x00, 0xfa, 0xec, 0x02, 0xd3, 0xea, 0xa6, 0xd9, 0x56, 0x1a, 0x15, 0x65, 0xa7, 0xb0, 0x5c, 0x63, 0x66, + 0xd0, 0x9d, 0xa7, 0xa5, 0x37, 0xf2, 0x0c, 0x7b, 0x28, 0x59, 0xa8, 0x3e, 0x02, 0x9e, 0x13, 0xa9, 0xbd, 0x28, 0x91, 0x57, 0xc5, 0xb7, 0x4c, 0x84, 0xea, 0xa3, 0x07, 0x75, 0x3d, 0x43, 0x12, 0x02, + 0xa3, 0xd9, 0xb6, 0x16, 0x22, 0x18, 0xbe, 0xc5, 0x34, 0x69, 0x45, 0xbf, 0xef, 0x55, 0xb6, 0x24, 0xc5, 0xc6, 0xe3, 0x73, 0x35, 0x9b, 0xb1, 0xc4, 0x79, 0x95, 0x2b, 0xba, 0xba, 0x4d, 0x65, 0x55, + 0xc2, 0x76, 0x57, 0x3e, 0x51, 0x52, 0xb5, 0x53, 0x90, 0x19, 0x99, 0xf6, 0x94, 0x02, 0xd1, 0x50, 0xbe, 0xf7, 0x9d, 0x74, 0xfb, 0x29, 0x53, 0x01, 0x8f, 0xf4, 0x86, 0x66, 0x74, 0x6a, 0xce, 0x60, + 0x78, 0x14, 0xa1, 0xfa, 0x33, 0x19, 0x57, 0x20, 0xf8, 0x38, 0x78, 0xd3, 0xb5, 0x75, 0xc7, 0x25, 0x74, 0x4a, 0x72, 0x07, 0x0d, 0xd0, 0x44, 0x01, 0x80, 0x42, 0xda, 0x25, 0x71, 0x4d, 0x17, 0x30, + 0x90, 0x32, 0x3a, 0x51, 0xe6, 0xc0, 0x63, 0xd2, 0x03, 0x88, 0x13, 0x80, 0x91, 0x27, 0x61, 0xfc, 0x34, 0x10, 0x83, 0x90, 0x95, 0xf2, 0x6c, 0x0e, 0x68, 0x7a, 0x00, 0x70, 0x54, 0x95, 0xe1, 0x71, + 0xb5, 0x71, 0x51, 0xac, 0xe0, 0x49, 0x8e, 0x30, 0xf1, 0x4c, 0xa9, 0xb0, 0x2f, 0x6e, 0x40, 0x83, 0x18, 0x54, 0xc2, 0xe0, 0xab, 0x1e, 0xcd, 0x0c, 0x21, 0xd8, 0xe4, 0xc7, 0xe6, 0x69, 0xcd, 0x72, + 0x82, 0x30, 0xb9, 0xd1, 0x1f, 0x72, 0xc2, 0x66, 0xe3, 0x44, 0x66, 0xf9, 0xc0, 0x15, 0x9e, 0xf4, 0x24, 0xf8, 0xf3, 0x1d, 0x95, 0xa5, 0x7b, 0xa0, 0xe2, 0x10, 0x54, 0x3c, 0x10, 0xc6, 0x50, 0x3f, + 0xb5, 0xc6, 0x3e, 0xd2, 0x3a, 0xa3, 0x6c, 0xd6, 0xa6, 0xf3, 0x78, 0x26, 0x1b, 0x0b, 0x1e, 0x79, 0x50, 0x9d, 0x8b, 0xeb, 0x36, 0xaa, 0x26, 0x3d, 0xc9, 0x15, 0x45, 0xe5, 0x33, 0x69, 0xdf, 0x26, + 0x83, 0x7f, 0x39, 0x4c, 0x56, 0x77, 0x7c, 0x95, 0xb6, 0x48, 0xbd, 0x1a, 0x72, 0x92, 0x1a, 0xbf, 0x49, 0x56, 0x3f, 0x99, 0xcb, 0x9d, 0x98, 0xea, 0xb5, 0xc6, 0x66, 0x66, 0xf6, 0xb1, 0x6f, 0x74, + 0x02, 0x24, 0x81, 0xfa, 0x21, 0x4e, 0x61, 0x76, 0x98, 0xd3, 0xbb, 0xd1, 0x3c, 0xb3, 0x08, 0x71, 0x3f, 0xdc, 0xc7, 0xcf, 0xd3, 0x97, 0xb9, 0xca, 0x39, 0xaf, 0xf4, 0xc7, 0x44, 0xd5, 0x71, 0x5d, + 0x58, 0x96, 0x6f, 0x2c, 0xf9, 0x70, 0x70, 0x15, 0xc8, 0xf3, 0x54, 0x3e, 0xd2, 0x86, 0xa3, 0xd8, 0xd5, 0xcb, 0xf6, 0x4a, 0xce, 0xdf, 0xc0, 0x29, 0x71, 0xa9, 0x10, 0x72, 0xc6, 0x9d, 0x2e, 0xf4, + 0x98, 0x29, 0xf1, 0x03, 0x7f, 0x05, 0x0c, 0x5b, 0x92, 0x22, 0x98, 0x56, 0xcb, 0x12, 0xb4, 0x56, 0xcc, 0x09, 0x52, 0x82, 0xa6, 0x26, 0x87, 0xea, 0x38, 0xc9, 0x77, 0x8a, 0xea, 0x49, 0x1d, 0xff, + 0x06, 0x97, 0x11, 0xfb, 0xbe, 0x05, 0xe8, 0xcd, 0x9b, 0xf4, 0x4a, 0x8e, 0x71, 0x26, 0x19, 0x57, 0x3e, 0x12, 0xea, 0xa7, 0xb2, 0x38, 0x29, 0xdc, 0x67, 0x26, 0xbf, 0xe3, 0x3d, 0xa1, 0x36, 0xb8, + 0x1e, 0x15, 0x32, 0x51, 0x50, 0x8f, 0x62, 0x85, 0xba, 0x15, 0xb2, 0xc1, 0x23, 0x76, 0x77, 0xfe, 0x5b, 0x14, 0xb4, 0xe3, 0x3f, 0x98, 0xc3, 0x26, 0xbc, 0x58, 0xb9, 0xd8, 0xe0, 0x75, 0xa2, 0x5b, + 0x94, 0xc8, 0xa2, 0x32, 0x33, 0x02, 0x9d, 0xcc, 0x78, 0x6b, 0x13, 0x5c, 0x56, 0x16, 0x4b, 0xa3, 0xd1, 0x60, 0xcb, 0xce, 0xa8, 0x54, 0xb7, 0x97, 0x1f, 0x9c, 0xd7, 0x3a, 0x38, 0x3a, 0xac, 0x05, + 0x0a, 0x30, 0x2a, 0xd8, 0x3b, 0x3e, 0x3a, 0xb9, 0x02, 0x46, 0xad, 0x16, 0x0a, 0x32, 0x1d, 0x33, 0x0a, 0xcd, 0xec, 0x7c, 0xa6, 0x64, 0x3d, 0x7e, 0xc0, 0x1f, 0x91, 0x69, 0x1f, 0x16, 0x32, 0x5b, + 0xdf, 0x39, 0x69, 0x50, 0xb8, 0x8d, 0xaf, 0xe3, 0x69, 0xc6, 0x54, 0xb8, 0x52, 0x05, 0x5c, 0x97, 0x03, 0x62, 0xc6, 0x13, 0x80, 0x46, 0x07, 0x57, 0xc6, 0x58, 0x90, 0xf4, 0xe5, 0x92, 0x22, 0xe4, + 0xa4, 0x06, 0x0b, 0x26, 0xc0, 0xeb, 0xc1, 0x01, 0x97, 0x59, 0x0d, 0xe3, 0xc8, 0xf0, 0x95, 0x5d, 0x65, 0x4b, 0x37, 0x1c, 0xcb, 0x90, 0xac, 0xa3, 0x71, 0xb2, 0x94, 0x47, 0x6c, 0x16, 0xa4, 0x59, + 0x6a, 0x1d, 0xe8, 0x30, 0x9e, 0x2a, 0x36, 0x12, 0xc6, 0x9b, 0x71, 0x25, 0x31, 0x05, 0x01, 0xe0, 0xc0, 0x49, 0xb8, 0x74, 0x40, 0xd9, 0xa6, 0xd0, 0xec, 0xb9, 0x99, 0xc9, 0xa0, 0x94, 0x2a, 0xa3, + 0x40, 0xf6, 0x03, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, 0x54, 0xa3, 0x16, 0x65, 0x29, + 0xb5, 0x39, 0x22, + }, + .secret_len = 32, + .secret = { + 0xed, 0x20, 0x14, 0x0c, 0x05, 0xd7, 0x8b, 0x15, 0xf2, 0xe4, 0x12, 0x67, 0x1a, 0x84, 0x15, 0x42, 0x17, 0xfd, 0x77, 0x61, 0x9a, 0x2c, 0x52, 0x2d, 0x3c, 0x3c, 0xb6, 0x88, 0xcb, 0x34, 0xc6, 0x8b, + }, + .cipher_len = 1088, + .cipher = { + 0xea, 0xdd, 0x5a, 0xda, 0x14, 0xda, 0x57, 0xf0, 0xae, 0xf3, 0x50, 0x5f, 0x1c, 0xaa, 0x64, 0x85, 0xd4, 0x23, 0x8d, 0x99, 0x9a, 0x3e, 0xf4, 0xb0, 0xa5, 0x9a, 0x1c, 0xdb, 0xe0, 0xa2, 0x7e, 0x47, + 0x85, 0x47, 0xa3, 0xa9, 0x9d, 0x2a, 0xb0, 0x9a, 0xc7, 0xd7, 0xc8, 0xf5, 0xae, 0x3d, 0x64, 0x32, 0x04, 0x5c, 0xba, 0x3f, 0xa7, 0x78, 0x34, 0x58, 0x92, 0x54, 0x2b, 0xd8, 0x1c, 0x05, 0xbe, 0xfc, + 0xd2, 0xe5, 0xcc, 0x9a, 0x57, 0x9b, 0xef, 0xb7, 0xc5, 0x8d, 0x02, 0xfb, 0x94, 0xf3, 0x33, 0x92, 0xfe, 0x17, 0xf4, 0xeb, 0xa2, 0xcb, 0x51, 0x0e, 0xc7, 0x4c, 0xc9, 0xd1, 0xd8, 0xa8, 0x7c, 0x10, + 0x66, 0xa4, 0x86, 0x9a, 0x39, 0x83, 0xe6, 0x64, 0xbf, 0xe9, 0xde, 0xa5, 0xae, 0x4f, 0xdf, 0x31, 0x0c, 0x8f, 0x59, 0x81, 0x5a, 0x67, 0x8f, 0xa3, 0x25, 0xf3, 0x69, 0xaf, 0x84, 0xff, 0xeb, 0xc1, + 0xd1, 0x50, 0x43, 0x1f, 0xe3, 0xbd, 0x27, 0x34, 0xf6, 0x36, 0xcf, 0x65, 0x8e, 0x6c, 0x1a, 0x6a, 0x6e, 0x2c, 0xbe, 0x07, 0x1f, 0x9a, 0x7c, 0x26, 0x11, 0x9a, 0xd1, 0x05, 0x09, 0x8e, 0xda, 0x62, + 0x2c, 0xab, 0x8e, 0x17, 0x67, 0x62, 0x10, 0x98, 0x77, 0xd9, 0xae, 0x9d, 0x67, 0x29, 0xd4, 0x4a, 0x58, 0xe7, 0x07, 0xd6, 0xb8, 0xad, 0x6e, 0x69, 0x6a, 0x33, 0xc6, 0x72, 0xda, 0x9d, 0x08, 0xda, + 0x2a, 0x7f, 0x9e, 0x3b, 0xf0, 0x22, 0x18, 0x23, 0x87, 0x22, 0xa4, 0x6b, 0x31, 0xd4, 0x9d, 0xaf, 0xf9, 0xaf, 0x00, 0xa6, 0x36, 0x3c, 0x3a, 0x42, 0x3b, 0x2e, 0x87, 0x3d, 0xef, 0xdd, 0xbc, 0xd9, + 0x69, 0xb7, 0x5a, 0x81, 0x05, 0x3d, 0x9a, 0x97, 0xc0, 0x6d, 0xe2, 0xbf, 0xe3, 0xd0, 0xcf, 0xd3, 0xd3, 0xc7, 0x79, 0x83, 0xb1, 0x8d, 0xbd, 0xe2, 0x3c, 0x07, 0x28, 0x60, 0x4a, 0x71, 0x43, 0x5a, + 0xd4, 0x0d, 0xf1, 0x57, 0x90, 0x96, 0xdd, 0xbe, 0x02, 0xe4, 0x61, 0x22, 0x10, 0xca, 0xa0, 0x34, 0xdc, 0xef, 0xb8, 0xb4, 0xd7, 0xb5, 0xe6, 0xd2, 0xeb, 0xa3, 0x7a, 0x79, 0xfb, 0x61, 0xf3, 0x4b, + 0x5a, 0xf7, 0xd9, 0xb2, 0x7b, 0x13, 0xe4, 0x93, 0x62, 0x22, 0x41, 0x12, 0x49, 0xb7, 0xfb, 0xb6, 0x9e, 0x73, 0x46, 0x1d, 0xaf, 0x4a, 0xa6, 0xf3, 0xe2, 0xc7, 0x39, 0x44, 0xf1, 0x0c, 0xe6, 0x7c, + 0x86, 0xfe, 0xd2, 0x60, 0xbd, 0xa7, 0xb4, 0x0d, 0xb3, 0x9b, 0x1d, 0xe3, 0xc7, 0xd8, 0xf0, 0x9a, 0x77, 0xf3, 0xc8, 0x4b, 0xc6, 0x29, 0x31, 0xd2, 0x28, 0xb2, 0x4a, 0x57, 0x4a, 0xc3, 0xf4, 0xeb, + 0x74, 0x5c, 0xff, 0x7e, 0x03, 0x1a, 0x3f, 0xb2, 0xa0, 0x85, 0x95, 0xc1, 0x53, 0x70, 0xa3, 0xc8, 0x2d, 0xb7, 0xd9, 0xf4, 0x1b, 0xb1, 0xd8, 0xec, 0xc4, 0x29, 0xcf, 0xa3, 0xa6, 0x58, 0x33, 0x01, + 0x6a, 0xb6, 0xea, 0x60, 0xc9, 0x39, 0x0c, 0xfa, 0x1b, 0x65, 0xcc, 0xea, 0xe5, 0x50, 0x94, 0x07, 0x95, 0x38, 0x6e, 0xd2, 0x41, 0x33, 0xfb, 0xae, 0x8b, 0x30, 0x17, 0x50, 0x2a, 0xf3, 0xcf, 0xe9, + 0x51, 0xd7, 0x81, 0xd3, 0x6c, 0xfe, 0xff, 0x85, 0xbf, 0xdf, 0x5a, 0xf0, 0x40, 0xbe, 0x40, 0x65, 0x68, 0x1b, 0x3b, 0x0a, 0x63, 0xc2, 0x74, 0x7f, 0x08, 0x08, 0xcf, 0x3d, 0xa7, 0x25, 0x16, 0x9d, + 0xde, 0xd1, 0x00, 0x3d, 0xa6, 0xcd, 0x5d, 0xe4, 0xcb, 0x04, 0x19, 0x42, 0x93, 0x8d, 0x0a, 0x7f, 0x88, 0x02, 0xd4, 0x8f, 0x2e, 0x3c, 0x6e, 0xeb, 0x45, 0xcd, 0x90, 0xaf, 0x6f, 0xc9, 0xf4, 0x50, + 0x7e, 0x9f, 0x83, 0x80, 0xac, 0x33, 0xca, 0xca, 0x77, 0x51, 0x48, 0x7f, 0x65, 0x50, 0x04, 0x41, 0xd9, 0x20, 0xb9, 0x48, 0x80, 0xa4, 0x97, 0xd0, 0x1c, 0x08, 0x02, 0xbb, 0x08, 0xd7, 0x4c, 0x5d, + 0x4c, 0x6b, 0xf2, 0xd8, 0x65, 0xee, 0x58, 0x22, 0xb3, 0x37, 0x5c, 0x75, 0x5d, 0x1a, 0x5e, 0x3d, 0x32, 0x44, 0xc3, 0x20, 0x51, 0x0a, 0x1e, 0x30, 0x35, 0x77, 0x02, 0xcd, 0x42, 0x52, 0x07, 0x2c, + 0xf8, 0x64, 0x37, 0xf7, 0xa9, 0xde, 0x55, 0x61, 0xc7, 0xe5, 0x9b, 0x94, 0xb9, 0x58, 0x41, 0x00, 0x13, 0x1a, 0xc3, 0x99, 0xf4, 0xc1, 0xeb, 0x19, 0xfb, 0x4b, 0xdf, 0x65, 0xe6, 0x27, 0x85, 0xe9, + 0x7c, 0x19, 0x4b, 0x87, 0x64, 0xcc, 0xf3, 0x2f, 0xd0, 0x5d, 0x80, 0x4c, 0x2e, 0x43, 0x9d, 0xda, 0x2a, 0x10, 0x92, 0x74, 0xfb, 0xff, 0xa8, 0x1a, 0x83, 0x7c, 0x51, 0xb2, 0x6d, 0x15, 0x4f, 0x97, + 0x4b, 0x88, 0x2a, 0x5b, 0x17, 0x4b, 0x30, 0x8f, 0xc4, 0x87, 0x68, 0xd2, 0x22, 0x92, 0x25, 0x32, 0xb1, 0x83, 0xab, 0xdf, 0x6f, 0xbb, 0x0b, 0xc7, 0x49, 0x27, 0x66, 0x97, 0x4d, 0x32, 0x1e, 0xe6, + 0xfb, 0x7c, 0x5f, 0x7b, 0x3e, 0xea, 0x23, 0x78, 0xdc, 0x6d, 0x6b, 0xb4, 0x80, 0x19, 0x25, 0x0b, 0x8d, 0x8d, 0x8d, 0xed, 0xb5, 0x22, 0x42, 0x1a, 0xee, 0xdb, 0x31, 0x86, 0x76, 0x98, 0x2a, 0x80, + 0xe7, 0x96, 0x1e, 0xc4, 0x0e, 0x6d, 0x7f, 0x33, 0x39, 0x69, 0x42, 0x55, 0xba, 0xff, 0x51, 0xbe, 0x3a, 0x7e, 0xa7, 0xd8, 0x79, 0x3a, 0x10, 0x9b, 0xe3, 0xae, 0x44, 0x23, 0xbf, 0x08, 0x2e, 0x20, + 0x6a, 0x57, 0x3b, 0x4f, 0x0f, 0x93, 0xfc, 0x16, 0xdd, 0xe8, 0x1b, 0xd5, 0xdc, 0x58, 0x3f, 0x52, 0x8c, 0x08, 0xa0, 0xa9, 0xab, 0x8e, 0x6c, 0xd5, 0x24, 0xe2, 0x97, 0xc9, 0xcf, 0x0f, 0x43, 0xc3, + 0x44, 0x91, 0x38, 0x30, 0xec, 0xb1, 0x6f, 0x91, 0x44, 0x14, 0x77, 0xba, 0x78, 0x2e, 0xdd, 0x4e, 0x73, 0xe7, 0x32, 0x97, 0x9d, 0x3a, 0x66, 0x4e, 0xb9, 0x9e, 0xa5, 0xd2, 0x4b, 0x6c, 0x84, 0xaa, + 0x69, 0xf3, 0x77, 0xcb, 0x0c, 0xad, 0x5a, 0xe4, 0xe6, 0x41, 0xe3, 0x8b, 0x19, 0x7a, 0x09, 0x94, 0xd5, 0x8b, 0x23, 0x87, 0xe9, 0x17, 0x60, 0xe9, 0xb6, 0xfe, 0xbc, 0xb4, 0x45, 0xcf, 0x85, 0xbb, + 0xa2, 0x4a, 0x94, 0xcd, 0xa7, 0x5e, 0x33, 0x86, 0x74, 0x42, 0x82, 0x49, 0xfe, 0x6d, 0xe4, 0x69, 0x26, 0x01, 0xd1, 0xea, 0xe0, 0xea, 0x02, 0x1d, 0x9b, 0xc8, 0x07, 0x7b, 0xe8, 0x66, 0x5d, 0x07, + 0x37, 0x74, 0x8f, 0xa3, 0x0f, 0xcf, 0x80, 0xf7, 0xe4, 0x82, 0x58, 0x46, 0x74, 0xf6, 0x33, 0xa5, 0x00, 0x6a, 0x53, 0x82, 0x67, 0x62, 0x7f, 0xd9, 0x18, 0x54, 0xe0, 0x87, 0x12, 0x68, 0xa6, 0xb0, + 0xb0, 0x5d, 0xd5, 0x14, 0x95, 0x13, 0x5d, 0xef, 0xb9, 0x37, 0x6e, 0x9b, 0x84, 0x1b, 0x64, 0xe5, 0xdb, 0xf4, 0x3c, 0xe6, 0xc7, 0x4b, 0xcf, 0x3a, 0xe1, 0xfc, 0x42, 0x7e, 0x81, 0x0b, 0x7c, 0xbf, + 0x69, 0x57, 0xdb, 0xf9, 0x04, 0x69, 0x0e, 0x87, 0x84, 0x25, 0x43, 0x89, 0x7d, 0xe7, 0x8f, 0x13, 0xd0, 0x8d, 0x92, 0xeb, 0xd2, 0x7f, 0xb2, 0xcf, 0xcc, 0x0c, 0x76, 0x54, 0x30, 0x58, 0x90, 0x57, + 0xb1, 0x6b, 0x15, 0xf2, 0x07, 0xca, 0x1e, 0x6f, 0x08, 0xd5, 0x26, 0x16, 0xdd, 0x57, 0xad, 0x43, 0xef, 0xea, 0x6f, 0xdd, 0xaa, 0xea, 0x18, 0xd3, 0x37, 0x31, 0xfa, 0xc7, 0xec, 0xaa, 0xe9, 0x50, + 0xe1, 0xdf, 0x3c, 0x5a, 0x4e, 0x6f, 0xcb, 0x22, 0x3d, 0xf5, 0xe8, 0x6b, 0x48, 0x7f, 0xd7, 0x09, 0x2d, 0x08, 0x22, 0xef, 0xfa, 0xec, 0x82, 0xc4, 0xbe, 0xc1, 0x0c, 0x60, 0x0f, 0xdb, 0x90, 0xe7, + 0x74, 0x82, 0x91, 0x1b, 0x15, 0x95, 0x27, 0x77, 0x38, 0x84, 0x14, 0x09, 0xd0, 0xf8, 0xf1, 0x13, 0x19, 0x1d, 0x47, 0xf5, 0xe5, 0x6c, 0x11, 0x5a, 0x05, 0xde, 0xa7, 0x59, 0xaa, 0x6f, 0xb1, 0xd0, + 0x47, 0xf9, 0xfc, 0xa4, 0xed, 0x51, 0x9e, 0xa5, 0xd2, 0x1f, 0xe3, 0xba, 0x5b, 0x94, 0x34, 0xfe, 0xa1, 0x28, 0x3d, 0xfa, 0xd6, 0x3d, 0x01, 0x58, 0x9b, 0x0e, 0xb6, 0x1f, 0x24, 0x43, 0x51, 0xd0, + 0x33, 0x41, 0xdc, 0xd4, 0xdf, 0x62, 0x26, 0x5a, 0xfc, 0xae, 0xc6, 0x67, 0x6a, 0x87, 0x7d, 0x5c, 0xac, 0xb3, 0x59, 0xeb, 0xb5, 0x31, 0x96, 0x10, 0xdd, 0x44, 0x7d, 0xa9, 0x7e, 0x95, 0x0b, 0x0c, + }, + }, + { + .name = "Kyber Round 2, 786 KAT 0", + .version = 0, + .keyform = CK_IBM_KYBER_KEYFORM_ROUND2_768, + .sk_len = 2400, + .sk = { + 0x07, 0x63, 0x8F, 0xB6, 0x98, 0x68, 0xF3, 0xD3, 0x20, 0xE5, 0x86, 0x2B, 0xD9, 0x69, 0x33, 0xFE, 0xB3, 0x11, 0xB3, 0x62, 0x09, 0x3C, 0x9B, 0x5D, 0x50, 0x17, 0x0B, 0xCE, 0xD4, 0x3F, 0x1B, 0x53, + 0x6D, 0x9A, 0x20, 0x4B, 0xB1, 0xF2, 0x26, 0x95, 0x95, 0x0B, 0xA1, 0xF2, 0xA9, 0xE8, 0xEB, 0x82, 0x8B, 0x28, 0x44, 0x88, 0x76, 0x0B, 0x3F, 0xC8, 0x4F, 0xAB, 0xA0, 0x42, 0x75, 0xD5, 0x62, 0x8E, + 0x39, 0xC5, 0xB2, 0x47, 0x13, 0x74, 0x28, 0x3C, 0x50, 0x32, 0x99, 0xC0, 0xAB, 0x49, 0xB6, 0x6B, 0x8B, 0xBB, 0x56, 0xA4, 0x18, 0x66, 0x24, 0xF9, 0x19, 0xA2, 0xBA, 0x59, 0xBB, 0x08, 0xD8, 0x55, + 0x18, 0x80, 0xC2, 0xBE, 0xFC, 0x4F, 0x87, 0xF2, 0x5F, 0x59, 0xAB, 0x58, 0x7A, 0x79, 0xC3, 0x27, 0xD7, 0x92, 0xD5, 0x4C, 0x97, 0x4A, 0x69, 0x26, 0x2F, 0xF8, 0xA7, 0x89, 0x38, 0x28, 0x9E, 0x9A, + 0x87, 0xB6, 0x88, 0xB0, 0x83, 0xE0, 0x59, 0x5F, 0xE2, 0x18, 0xB6, 0xBB, 0x15, 0x05, 0x94, 0x1C, 0xE2, 0xE8, 0x1A, 0x5A, 0x64, 0xC5, 0xAA, 0xC6, 0x04, 0x17, 0x25, 0x69, 0x85, 0x34, 0x9E, 0xE4, + 0x7A, 0x52, 0x42, 0x0A, 0x5F, 0x97, 0x47, 0x7B, 0x72, 0x36, 0xAC, 0x76, 0xBC, 0x70, 0xE8, 0x28, 0x87, 0x29, 0x28, 0x7E, 0xE3, 0xE3, 0x4A, 0x3D, 0xBC, 0x36, 0x83, 0xC0, 0xB7, 0xB1, 0x00, 0x29, + 0xFC, 0x20, 0x34, 0x18, 0x53, 0x7E, 0x74, 0x66, 0xBA, 0x63, 0x85, 0xA8, 0xFF, 0x30, 0x1E, 0xE1, 0x27, 0x08, 0xF8, 0x2A, 0xAA, 0x1E, 0x38, 0x0F, 0xC7, 0xA8, 0x8F, 0x8F, 0x20, 0x5A, 0xB7, 0xE8, + 0x8D, 0x7E, 0x95, 0x95, 0x2A, 0x55, 0xBA, 0x20, 0xD0, 0x9B, 0x79, 0xA4, 0x71, 0x41, 0xD6, 0x2B, 0xF6, 0xEB, 0x7D, 0xD3, 0x07, 0xB0, 0x8E, 0xCA, 0x13, 0xA5, 0xBC, 0x5F, 0x6B, 0x68, 0x58, 0x1C, + 0x68, 0x65, 0xB2, 0x7B, 0xBC, 0xDD, 0xAB, 0x14, 0x2F, 0x4B, 0x2C, 0xBF, 0xF4, 0x88, 0xC8, 0xA2, 0x27, 0x05, 0xFA, 0xA9, 0x8A, 0x2B, 0x9E, 0xEA, 0x35, 0x30, 0xC7, 0x66, 0x62, 0x33, 0x5C, 0xC7, + 0xEA, 0x3A, 0x00, 0x77, 0x77, 0x25, 0xEB, 0xCC, 0xCD, 0x2A, 0x46, 0x36, 0xB2, 0xD9, 0x12, 0x2F, 0xF3, 0xAB, 0x77, 0x12, 0x3C, 0xE0, 0x88, 0x3C, 0x19, 0x11, 0x11, 0x5E, 0x50, 0xC9, 0xE8, 0xA9, + 0x41, 0x94, 0xE4, 0x8D, 0xD0, 0xD0, 0x9C, 0xFF, 0xB3, 0xAD, 0xCD, 0x2C, 0x1E, 0x92, 0x43, 0x09, 0x03, 0xD0, 0x7A, 0xDB, 0xF0, 0x05, 0x32, 0x03, 0x15, 0x75, 0xAA, 0x7F, 0x9E, 0x7B, 0x5A, 0x1F, + 0x33, 0x62, 0xDE, 0xC9, 0x36, 0xD4, 0x04, 0x3C, 0x05, 0xF2, 0x47, 0x6C, 0x07, 0x57, 0x8B, 0xC9, 0xCB, 0xAF, 0x2A, 0xB4, 0xE3, 0x82, 0x72, 0x7A, 0xD4, 0x16, 0x86, 0xA9, 0x6B, 0x25, 0x48, 0x82, + 0x0B, 0xB0, 0x3B, 0x32, 0xF1, 0x1B, 0x28, 0x11, 0xAD, 0x62, 0xF4, 0x89, 0xE9, 0x51, 0x63, 0x2A, 0xBA, 0x0D, 0x1D, 0xF8, 0x96, 0x80, 0xCC, 0x8A, 0x8B, 0x53, 0xB4, 0x81, 0xD9, 0x2A, 0x68, 0xD7, + 0x0B, 0x4E, 0xA1, 0xC3, 0xA6, 0xA5, 0x61, 0xC0, 0x69, 0x28, 0x82, 0xB5, 0xCA, 0x8C, 0xC9, 0x42, 0xA8, 0xD4, 0x95, 0xAF, 0xCB, 0x06, 0xDE, 0x89, 0x49, 0x8F, 0xB9, 0x35, 0xB7, 0x75, 0x90, 0x8F, + 0xE7, 0xA0, 0x3E, 0x32, 0x4D, 0x54, 0xCC, 0x19, 0xD4, 0xE1, 0xAA, 0xBD, 0x35, 0x93, 0xB3, 0x8B, 0x19, 0xEE, 0x13, 0x88, 0xFE, 0x49, 0x2B, 0x43, 0x12, 0x7E, 0x5A, 0x50, 0x42, 0x53, 0x78, 0x6A, + 0x0D, 0x69, 0xAD, 0x32, 0x60, 0x1C, 0x28, 0xE2, 0xC8, 0x85, 0x04, 0xA5, 0xBA, 0x59, 0x97, 0x06, 0x02, 0x3A, 0x61, 0x36, 0x3E, 0x17, 0xC6, 0xB9, 0xBB, 0x59, 0xBD, 0xC6, 0x97, 0x45, 0x2C, 0xD0, + 0x59, 0x45, 0x19, 0x83, 0xD7, 0x38, 0xCA, 0x3F, 0xD0, 0x34, 0xE3, 0xF5, 0x98, 0x88, 0x54, 0xCA, 0x05, 0x03, 0x1D, 0xB0, 0x96, 0x11, 0x49, 0x89, 0x88, 0x19, 0x7C, 0x6B, 0x30, 0xD2, 0x58, 0xDF, + 0xE2, 0x62, 0x65, 0x54, 0x1C, 0x89, 0xA4, 0xB3, 0x1D, 0x68, 0x64, 0xE9, 0x38, 0x9B, 0x03, 0xCB, 0x74, 0xF7, 0xEC, 0x43, 0x23, 0xFB, 0x94, 0x21, 0xA4, 0xB9, 0x79, 0x0A, 0x26, 0xD1, 0x7B, 0x03, + 0x98, 0xA2, 0x67, 0x67, 0x35, 0x09, 0x09, 0xF8, 0x4D, 0x57, 0xB6, 0x69, 0x4D, 0xF8, 0x30, 0x66, 0x4C, 0xA8, 0xB3, 0xC3, 0xC0, 0x3E, 0xD2, 0xAE, 0x67, 0xB8, 0x90, 0x06, 0x86, 0x8A, 0x68, 0x52, + 0x7C, 0xCD, 0x66, 0x64, 0x59, 0xAB, 0x7F, 0x05, 0x66, 0x71, 0x00, 0x0C, 0x61, 0x64, 0xD3, 0xA7, 0xF2, 0x66, 0xA1, 0x4D, 0x97, 0xCB, 0xD7, 0x00, 0x4D, 0x6C, 0x92, 0xCA, 0xCA, 0x77, 0x0B, 0x84, + 0x4A, 0x4F, 0xA9, 0xB1, 0x82, 0xE7, 0xB1, 0x8C, 0xA8, 0x85, 0x08, 0x2A, 0xC5, 0x64, 0x6F, 0xCB, 0x4A, 0x14, 0xE1, 0x68, 0x5F, 0xEB, 0x0C, 0x9C, 0xE3, 0x37, 0x2A, 0xB9, 0x53, 0x65, 0xC0, 0x4F, + 0xD8, 0x30, 0x84, 0xF8, 0x0A, 0x23, 0xFF, 0x10, 0xA0, 0x5B, 0xF1, 0x5F, 0x7F, 0xA5, 0xAC, 0xC6, 0xC0, 0xCB, 0x46, 0x2C, 0x33, 0xCA, 0x52, 0x4F, 0xA6, 0xB8, 0xBB, 0x35, 0x90, 0x43, 0xBA, 0x68, + 0x60, 0x9E, 0xAA, 0x25, 0x36, 0xE8, 0x1D, 0x08, 0x46, 0x3B, 0x19, 0x65, 0x3B, 0x54, 0x35, 0xBA, 0x94, 0x6C, 0x9A, 0xDD, 0xEB, 0x20, 0x2B, 0x04, 0xB0, 0x31, 0xCC, 0x96, 0x0D, 0xCC, 0x12, 0xE4, + 0x51, 0x8D, 0x42, 0x8B, 0x32, 0xB2, 0x57, 0xA4, 0xFC, 0x73, 0x13, 0xD3, 0xA7, 0x98, 0x0D, 0x80, 0x08, 0x2E, 0x93, 0x4F, 0x9D, 0x95, 0xC3, 0x2B, 0x0A, 0x01, 0x91, 0xA2, 0x36, 0x04, 0x38, 0x4D, + 0xD9, 0xE0, 0x79, 0xBB, 0xBA, 0xA2, 0x66, 0xD1, 0x4C, 0x3F, 0x75, 0x6B, 0x9F, 0x21, 0x33, 0x10, 0x74, 0x33, 0xA4, 0xE8, 0x3F, 0xA7, 0x18, 0x72, 0x82, 0xA8, 0x09, 0x20, 0x3A, 0x4F, 0xAF, 0x84, + 0x18, 0x51, 0x83, 0x3D, 0x12, 0x1A, 0xC3, 0x83, 0x84, 0x3A, 0x5E, 0x55, 0xBC, 0x23, 0x81, 0x42, 0x5E, 0x16, 0xC7, 0xDB, 0x4C, 0xC9, 0xAB, 0x5C, 0x1B, 0x0D, 0x91, 0xA4, 0x7E, 0x2B, 0x8D, 0xE0, + 0xE5, 0x82, 0xC8, 0x6B, 0x6B, 0x0D, 0x90, 0x7B, 0xB3, 0x60, 0xB9, 0x7F, 0x40, 0xAB, 0x5D, 0x03, 0x8F, 0x6B, 0x75, 0xC8, 0x14, 0xB2, 0x7D, 0x9B, 0x96, 0x8D, 0x41, 0x98, 0x32, 0xBC, 0x8C, 0x2B, + 0xEE, 0x60, 0x5E, 0xF6, 0xE5, 0x05, 0x9D, 0x33, 0x10, 0x0D, 0x90, 0x48, 0x5D, 0x37, 0x84, 0x50, 0x01, 0x42, 0x21, 0x73, 0x6C, 0x07, 0x40, 0x7C, 0xAC, 0x26, 0x04, 0x08, 0xAA, 0x64, 0x92, 0x66, + 0x19, 0x78, 0x8B, 0x86, 0x01, 0xC2, 0xA7, 0x52, 0xD1, 0xA6, 0xCB, 0xF8, 0x20, 0xD7, 0xC7, 0xA0, 0x47, 0x16, 0x20, 0x32, 0x25, 0xB3, 0x89, 0x5B, 0x93, 0x42, 0xD1, 0x47, 0xA8, 0x18, 0x5C, 0xFC, + 0x1B, 0xB6, 0x5B, 0xA0, 0x6B, 0x41, 0x42, 0x33, 0x99, 0x03, 0xC0, 0xAC, 0x46, 0x51, 0x38, 0x5B, 0x45, 0xD9, 0x8A, 0x8B, 0x19, 0xD2, 0x8C, 0xD6, 0xBA, 0xB0, 0x88, 0x78, 0x7F, 0x7E, 0xE1, 0xB1, + 0x24, 0x61, 0x76, 0x6B, 0x43, 0xCB, 0xCC, 0xB9, 0x64, 0x34, 0x42, 0x7D, 0x93, 0xC0, 0x65, 0x55, 0x06, 0x88, 0xF6, 0x94, 0x8E, 0xD1, 0xB5, 0x47, 0x5A, 0x42, 0x5F, 0x1B, 0x85, 0x20, 0x9D, 0x06, + 0x1C, 0x08, 0xB5, 0x6C, 0x1C, 0xC0, 0x69, 0xF6, 0xC0, 0xA7, 0xC6, 0xF2, 0x93, 0x58, 0xCA, 0xB9, 0x11, 0x08, 0x77, 0x32, 0xA6, 0x49, 0xD2, 0x7C, 0x9B, 0x98, 0xF9, 0xA4, 0x88, 0x79, 0x38, 0x7D, + 0x9B, 0x00, 0xC2, 0x59, 0x59, 0xA7, 0x16, 0x54, 0xD6, 0xF6, 0xA9, 0x46, 0x16, 0x45, 0x13, 0xE4, 0x7A, 0x75, 0xD0, 0x05, 0x98, 0x6C, 0x23, 0x63, 0xC0, 0x9F, 0x6B, 0x53, 0x7E, 0xCA, 0x78, 0xB9, + 0x30, 0x3A, 0x5F, 0xA4, 0x57, 0x60, 0x8A, 0x58, 0x6A, 0x65, 0x3A, 0x34, 0x7D, 0xB0, 0x4D, 0xFC, 0xC1, 0x91, 0x75, 0xB3, 0xA3, 0x01, 0x17, 0x25, 0x36, 0x06, 0x2A, 0x65, 0x8A, 0x95, 0x27, 0x75, + 0x70, 0xC8, 0x85, 0x2C, 0xA8, 0x97, 0x3F, 0x4A, 0xE1, 0x23, 0xA3, 0x34, 0x04, 0x7D, 0xD7, 0x11, 0xC8, 0x92, 0x7A, 0x63, 0x4A, 0x03, 0x38, 0x8A, 0x52, 0x7B, 0x03, 0x4B, 0xF7, 0xA8, 0x17, 0x0F, + 0xA7, 0x02, 0xC1, 0xF7, 0xC2, 0x3E, 0xC3, 0x2D, 0x18, 0xA2, 0x37, 0x48, 0x90, 0xBE, 0x9C, 0x78, 0x7A, 0x94, 0x09, 0xC8, 0x2D, 0x19, 0x2C, 0x4B, 0xB7, 0x05, 0xA2, 0xF9, 0x96, 0xCE, 0x40, 0x5D, + 0xA0, 0xB7, 0x1F, 0x67, 0xC6, 0xCE, 0xC0, 0xD3, 0x56, 0x86, 0xD5, 0x13, 0x42, 0x34, 0x32, 0xE5, 0x12, 0xAC, 0x40, 0x44, 0x55, 0x7E, 0x86, 0x8A, 0x62, 0x48, 0x00, 0x10, 0x9A, 0x33, 0x55, 0xF9, + 0x8F, 0x15, 0x14, 0x44, 0xE2, 0x85, 0x2E, 0x27, 0xEA, 0x6E, 0xDB, 0x19, 0x92, 0xCA, 0xD3, 0x97, 0x3C, 0x3A, 0x6F, 0xF7, 0x9A, 0x5A, 0x04, 0x9A, 0x25, 0x9E, 0xB5, 0x41, 0x5A, 0xA2, 0xA2, 0x62, + 0x45, 0x6E, 0xC9, 0x49, 0x5B, 0xBB, 0x52, 0x00, 0xD8, 0xD3, 0x16, 0x3A, 0x5B, 0x10, 0x22, 0x62, 0x92, 0xEC, 0xA0, 0x10, 0x21, 0x38, 0x9D, 0xA3, 0x78, 0x81, 0xE2, 0x76, 0x30, 0x65, 0x50, 0xC6, + 0xEF, 0xB6, 0x44, 0x0E, 0xC5, 0x1A, 0x2F, 0x73, 0x48, 0x34, 0x9B, 0x85, 0x1C, 0xD4, 0xAA, 0x01, 0x75, 0xA0, 0x55, 0x02, 0x13, 0xC4, 0x79, 0x1D, 0x91, 0x01, 0x12, 0x20, 0x82, 0x4B, 0x2B, 0x61, + 0x65, 0x08, 0x13, 0xAD, 0xFD, 0x2C, 0xB1, 0x05, 0x38, 0xBF, 0xAB, 0x0A, 0x72, 0x6F, 0x81, 0x12, 0x9E, 0xD2, 0xC0, 0xF0, 0x6A, 0x16, 0xB7, 0x01, 0x09, 0x0B, 0xF0, 0x48, 0xC5, 0xA4, 0x01, 0x26, + 0xD5, 0x72, 0xFC, 0xD4, 0x7A, 0xA1, 0x21, 0x8F, 0xB0, 0x15, 0x47, 0xD1, 0x50, 0x79, 0x2D, 0x23, 0x16, 0xCB, 0x32, 0x0D, 0x51, 0x44, 0xBA, 0x35, 0x08, 0xA1, 0xEB, 0xBB, 0x5A, 0xC1, 0xC2, 0x29, + 0x13, 0xE8, 0x29, 0x5F, 0xAB, 0x59, 0xBF, 0x58, 0x37, 0xA7, 0x78, 0xCF, 0x28, 0x22, 0x7E, 0x07, 0xE1, 0x03, 0x2D, 0xAB, 0x7D, 0x0E, 0x09, 0xA1, 0x5F, 0x13, 0x41, 0x48, 0xC1, 0x20, 0x09, 0xDA, + 0x53, 0x6B, 0x22, 0xCC, 0x62, 0x47, 0x4E, 0x69, 0xCC, 0x15, 0x54, 0xC0, 0x81, 0x4D, 0x6C, 0xA0, 0xB7, 0x22, 0x59, 0x43, 0x83, 0xA9, 0xD0, 0xA2, 0xC7, 0x7F, 0xD3, 0x65, 0xA5, 0x54, 0x42, 0x95, + 0xFB, 0xB9, 0x73, 0xF9, 0x1E, 0xA5, 0x64, 0x90, 0xD6, 0xCA, 0x68, 0x76, 0x49, 0x7B, 0x98, 0xB3, 0xCB, 0x12, 0x41, 0x7C, 0x25, 0x7B, 0x6D, 0x0F, 0x71, 0x83, 0xDB, 0xB6, 0x9E, 0x33, 0x07, 0x5B, + 0xEB, 0x01, 0x17, 0xB6, 0x91, 0x4C, 0x69, 0xBA, 0x38, 0x34, 0x94, 0x22, 0xF2, 0xF4, 0x33, 0x64, 0x82, 0x2A, 0x25, 0x70, 0x95, 0x2D, 0xD5, 0x07, 0x7B, 0x90, 0x75, 0x5F, 0x15, 0x74, 0x11, 0x5B, + 0x8E, 0x22, 0x14, 0x27, 0x58, 0x59, 0x61, 0x91, 0x3A, 0x9B, 0xFA, 0x05, 0x02, 0xB5, 0xD7, 0x9A, 0xB7, 0x81, 0x17, 0x44, 0xE6, 0x56, 0x3C, 0x5B, 0x62, 0xC5, 0xCC, 0x4E, 0x93, 0x23, 0x9A, 0x0A, + 0x8C, 0xC6, 0x0F, 0xE8, 0x48, 0xF8, 0x4A, 0x95, 0xF5, 0x90, 0x25, 0x99, 0xB5, 0x4A, 0x06, 0x62, 0x93, 0xA2, 0x02, 0x1D, 0xA1, 0x96, 0x76, 0x6C, 0x17, 0xC7, 0xE8, 0x63, 0xAF, 0x79, 0x0C, 0x27, + 0x0B, 0x21, 0x6A, 0x25, 0x13, 0x8D, 0xDA, 0x0C, 0x81, 0x26, 0xE0, 0x93, 0x77, 0x87, 0x98, 0x59, 0xDB, 0x35, 0x8F, 0x9B, 0x82, 0xB7, 0xC8, 0xA6, 0x79, 0x2A, 0xCE, 0xE9, 0x2A, 0x4C, 0xBD, 0xE3, + 0xCE, 0xDD, 0x45, 0x00, 0xAC, 0xBC, 0x55, 0x5C, 0x28, 0x8E, 0xFF, 0x97, 0x95, 0x26, 0x5B, 0x90, 0x05, 0x35, 0x1C, 0x52, 0xE2, 0x65, 0x35, 0x54, 0xAB, 0xAA, 0xF8, 0x72, 0xDF, 0x95, 0xCA, 0x7F, + 0x79, 0x59, 0x03, 0xF0, 0xB0, 0xA1, 0x82, 0xB1, 0x8A, 0xEB, 0x04, 0x75, 0xB2, 0x9F, 0x6E, 0x3A, 0xBF, 0x4C, 0x22, 0x50, 0xFE, 0x7B, 0x84, 0x2A, 0x73, 0x65, 0x50, 0x16, 0xA8, 0xFC, 0x72, 0x9F, + 0x39, 0x05, 0x07, 0xAC, 0xA9, 0x36, 0x82, 0x5A, 0x98, 0xB3, 0xA3, 0x2E, 0x6B, 0x25, 0x54, 0xCE, 0x95, 0x28, 0x94, 0x1A, 0x3B, 0xB8, 0xC9, 0x09, 0x96, 0x00, 0x8D, 0x74, 0xFB, 0xCD, 0x02, 0x0A, + 0x02, 0xE7, 0x06, 0xA6, 0xDE, 0x7B, 0x02, 0xAF, 0x40, 0x4C, 0x10, 0xDB, 0x00, 0xFA, 0xEC, 0x02, 0xD3, 0xEA, 0xA6, 0xD9, 0x56, 0x1A, 0x15, 0x65, 0xA7, 0xB0, 0x5C, 0x63, 0x66, 0xD0, 0x9D, 0xA7, + 0xA5, 0x37, 0xF2, 0x0C, 0x7B, 0x28, 0x59, 0xA8, 0x3E, 0x02, 0x9E, 0x13, 0xA9, 0xBD, 0x28, 0x91, 0x57, 0xC5, 0xB7, 0x4C, 0x84, 0xEA, 0xA3, 0x07, 0x75, 0x3D, 0x43, 0x12, 0x02, 0xA3, 0xD9, 0xB6, + 0x16, 0x22, 0x18, 0xBE, 0xC5, 0x34, 0x69, 0x45, 0xBF, 0xEF, 0x55, 0xB6, 0x24, 0xC5, 0xC6, 0xE3, 0x73, 0x35, 0x9B, 0xB1, 0xC4, 0x79, 0x95, 0x2B, 0xBA, 0xBA, 0x4D, 0x65, 0x55, 0xC2, 0x76, 0x57, + 0x3E, 0x51, 0x52, 0xB5, 0x53, 0x90, 0x19, 0x99, 0xF6, 0x94, 0x02, 0xD1, 0x50, 0xBE, 0xF7, 0x9D, 0x74, 0xFB, 0x29, 0x53, 0x01, 0x8F, 0xF4, 0x86, 0x66, 0x74, 0x6A, 0xCE, 0x60, 0x78, 0x14, 0xA1, + 0xFA, 0x33, 0x19, 0x57, 0x20, 0xF8, 0x38, 0x78, 0xD3, 0xB5, 0x75, 0xC7, 0x25, 0x74, 0x4A, 0x72, 0x07, 0x0D, 0xD0, 0x44, 0x01, 0x80, 0x42, 0xDA, 0x25, 0x71, 0x4D, 0x17, 0x30, 0x90, 0x32, 0x3A, + 0x51, 0xE6, 0xC0, 0x63, 0xD2, 0x03, 0x88, 0x13, 0x80, 0x91, 0x27, 0x61, 0xFC, 0x34, 0x10, 0x83, 0x90, 0x95, 0xF2, 0x6C, 0x0E, 0x68, 0x7A, 0x00, 0x70, 0x54, 0x95, 0xE1, 0x71, 0xB5, 0x71, 0x51, + 0xAC, 0xE0, 0x49, 0x8E, 0x30, 0xF1, 0x4C, 0xA9, 0xB0, 0x2F, 0x6E, 0x40, 0x83, 0x18, 0x54, 0xC2, 0xE0, 0xAB, 0x1E, 0xCD, 0x0C, 0x21, 0xD8, 0xE4, 0xC7, 0xE6, 0x69, 0xCD, 0x72, 0x82, 0x30, 0xB9, + 0xD1, 0x1F, 0x72, 0xC2, 0x66, 0xE3, 0x44, 0x66, 0xF9, 0xC0, 0x15, 0x9E, 0xF4, 0x24, 0xF8, 0xF3, 0x1D, 0x95, 0xA5, 0x7B, 0xA0, 0xE2, 0x10, 0x54, 0x3C, 0x10, 0xC6, 0x50, 0x3F, 0xB5, 0xC6, 0x3E, + 0xD2, 0x3A, 0xA3, 0x6C, 0xD6, 0xA6, 0xF3, 0x78, 0x26, 0x1B, 0x0B, 0x1E, 0x79, 0x50, 0x9D, 0x8B, 0xEB, 0x36, 0xAA, 0x26, 0x3D, 0xC9, 0x15, 0x45, 0xE5, 0x33, 0x69, 0xDF, 0x26, 0x83, 0x7F, 0x39, + 0x4C, 0x56, 0x77, 0x7C, 0x95, 0xB6, 0x48, 0xBD, 0x1A, 0x72, 0x92, 0x1A, 0xBF, 0x49, 0x56, 0x3F, 0x99, 0xCB, 0x9D, 0x98, 0xEA, 0xB5, 0xC6, 0x66, 0x66, 0xF6, 0xB1, 0x6F, 0x74, 0x02, 0x24, 0x81, + 0xFA, 0x21, 0x4E, 0x61, 0x76, 0x98, 0xD3, 0xBB, 0xD1, 0x3C, 0xB3, 0x08, 0x71, 0x3F, 0xDC, 0xC7, 0xCF, 0xD3, 0x97, 0xB9, 0xCA, 0x39, 0xAF, 0xF4, 0xC7, 0x44, 0xD5, 0x71, 0x5D, 0x58, 0x96, 0x6F, + 0x2C, 0xF9, 0x70, 0x70, 0x15, 0xC8, 0xF3, 0x54, 0x3E, 0xD2, 0x86, 0xA3, 0xD8, 0xD5, 0xCB, 0xF6, 0x4A, 0xCE, 0xDF, 0xC0, 0x29, 0x71, 0xA9, 0x10, 0x72, 0xC6, 0x9D, 0x2E, 0xF4, 0x98, 0x29, 0xF1, + 0x03, 0x7F, 0x05, 0x0C, 0x5B, 0x92, 0x22, 0x98, 0x56, 0xCB, 0x12, 0xB4, 0x56, 0xCC, 0x09, 0x52, 0x82, 0xA6, 0x26, 0x87, 0xEA, 0x38, 0xC9, 0x77, 0x8A, 0xEA, 0x49, 0x1D, 0xFF, 0x06, 0x97, 0x11, + 0xFB, 0xBE, 0x05, 0xE8, 0xCD, 0x9B, 0xF4, 0x4A, 0x8E, 0x71, 0x26, 0x19, 0x57, 0x3E, 0x12, 0xEA, 0xA7, 0xB2, 0x38, 0x29, 0xDC, 0x67, 0x26, 0xBF, 0xE3, 0x3D, 0xA1, 0x36, 0xB8, 0x1E, 0x15, 0x32, + 0x51, 0x50, 0x8F, 0x62, 0x85, 0xBA, 0x15, 0xB2, 0xC1, 0x23, 0x76, 0x77, 0xFE, 0x5B, 0x14, 0xB4, 0xE3, 0x3F, 0x98, 0xC3, 0x26, 0xBC, 0x58, 0xB9, 0xD8, 0xE0, 0x75, 0xA2, 0x5B, 0x94, 0xC8, 0xA2, + 0x32, 0x33, 0x02, 0x9D, 0xCC, 0x78, 0x6B, 0x13, 0x5C, 0x56, 0x16, 0x4B, 0xA3, 0xD1, 0x60, 0xCB, 0xCE, 0xA8, 0x54, 0xB7, 0x97, 0x1F, 0x9C, 0xD7, 0x3A, 0x38, 0x3A, 0xAC, 0x05, 0x0A, 0x30, 0x2A, + 0xD8, 0x3B, 0x3E, 0x3A, 0xB9, 0x02, 0x46, 0xAD, 0x16, 0x0A, 0x32, 0x1D, 0x33, 0x0A, 0xCD, 0xEC, 0x7C, 0xA6, 0x64, 0x3D, 0x7E, 0xC0, 0x1F, 0x91, 0x69, 0x1F, 0x16, 0x32, 0x5B, 0xDF, 0x39, 0x69, + 0x50, 0xB8, 0x8D, 0xAF, 0xE3, 0x69, 0xC6, 0x54, 0xB8, 0x52, 0x05, 0x5C, 0x97, 0x03, 0x62, 0xC6, 0x13, 0x80, 0x46, 0x07, 0x57, 0xC6, 0x58, 0x90, 0xF4, 0xE5, 0x92, 0x22, 0xE4, 0xA4, 0x06, 0x0B, + 0x26, 0xC0, 0xEB, 0xC1, 0x01, 0x97, 0x59, 0x0D, 0xE3, 0xC8, 0xF0, 0x95, 0x5D, 0x65, 0x4B, 0x37, 0x1C, 0xCB, 0x90, 0xAC, 0xA3, 0x71, 0xB2, 0x94, 0x47, 0x6C, 0x16, 0xA4, 0x59, 0x6A, 0x1D, 0xE8, + 0x30, 0x9E, 0x2A, 0x36, 0x12, 0xC6, 0x9B, 0x71, 0x25, 0x31, 0x05, 0x01, 0xE0, 0xC0, 0x49, 0xB8, 0x74, 0x40, 0xD9, 0xA6, 0xD0, 0xEC, 0xB9, 0x99, 0xC9, 0xA0, 0x94, 0x2A, 0xA3, 0x40, 0xF6, 0x03, + 0x65, 0xEA, 0xFD, 0x46, 0x5F, 0xC6, 0x4A, 0x0C, 0x5F, 0x8F, 0x3F, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9D, 0x59, 0xA5, 0x43, 0xD8, 0x20, 0x8C, 0x54, 0xA3, 0x16, 0x65, 0x29, 0xB5, 0x39, 0x22, + 0xDE, 0xE4, 0xAB, 0xA0, 0x00, 0x38, 0x95, 0x81, 0x71, 0x7D, 0x36, 0xF5, 0x6F, 0x39, 0xAF, 0x73, 0x00, 0xB3, 0x1D, 0x83, 0x1A, 0x4D, 0x8C, 0x97, 0x61, 0x28, 0xE0, 0x9D, 0xED, 0xE7, 0x1A, 0x5A, + 0x86, 0x26, 0xED, 0x79, 0xD4, 0x51, 0x14, 0x08, 0x00, 0xE0, 0x3B, 0x59, 0xB9, 0x56, 0xF8, 0x21, 0x0E, 0x55, 0x60, 0x67, 0x40, 0x7D, 0x13, 0xDC, 0x90, 0xFA, 0x9E, 0x8B, 0x87, 0x2B, 0xFB, 0x8F, + }, + .pk_len = 1184, + .pk = { + 0xA0, 0xB7, 0x1F, 0x67, 0xC6, 0xCE, 0xC0, 0xD3, 0x56, 0x86, 0xD5, 0x13, 0x42, 0x34, 0x32, 0xE5, 0x12, 0xAC, 0x40, 0x44, 0x55, 0x7E, 0x86, 0x8A, 0x62, 0x48, 0x00, 0x10, 0x9A, 0x33, 0x55, 0xF9, + 0x8F, 0x15, 0x14, 0x44, 0xE2, 0x85, 0x2E, 0x27, 0xEA, 0x6E, 0xDB, 0x19, 0x92, 0xCA, 0xD3, 0x97, 0x3C, 0x3A, 0x6F, 0xF7, 0x9A, 0x5A, 0x04, 0x9A, 0x25, 0x9E, 0xB5, 0x41, 0x5A, 0xA2, 0xA2, 0x62, + 0x45, 0x6E, 0xC9, 0x49, 0x5B, 0xBB, 0x52, 0x00, 0xD8, 0xD3, 0x16, 0x3A, 0x5B, 0x10, 0x22, 0x62, 0x92, 0xEC, 0xA0, 0x10, 0x21, 0x38, 0x9D, 0xA3, 0x78, 0x81, 0xE2, 0x76, 0x30, 0x65, 0x50, 0xC6, + 0xEF, 0xB6, 0x44, 0x0E, 0xC5, 0x1A, 0x2F, 0x73, 0x48, 0x34, 0x9B, 0x85, 0x1C, 0xD4, 0xAA, 0x01, 0x75, 0xA0, 0x55, 0x02, 0x13, 0xC4, 0x79, 0x1D, 0x91, 0x01, 0x12, 0x20, 0x82, 0x4B, 0x2B, 0x61, + 0x65, 0x08, 0x13, 0xAD, 0xFD, 0x2C, 0xB1, 0x05, 0x38, 0xBF, 0xAB, 0x0A, 0x72, 0x6F, 0x81, 0x12, 0x9E, 0xD2, 0xC0, 0xF0, 0x6A, 0x16, 0xB7, 0x01, 0x09, 0x0B, 0xF0, 0x48, 0xC5, 0xA4, 0x01, 0x26, + 0xD5, 0x72, 0xFC, 0xD4, 0x7A, 0xA1, 0x21, 0x8F, 0xB0, 0x15, 0x47, 0xD1, 0x50, 0x79, 0x2D, 0x23, 0x16, 0xCB, 0x32, 0x0D, 0x51, 0x44, 0xBA, 0x35, 0x08, 0xA1, 0xEB, 0xBB, 0x5A, 0xC1, 0xC2, 0x29, + 0x13, 0xE8, 0x29, 0x5F, 0xAB, 0x59, 0xBF, 0x58, 0x37, 0xA7, 0x78, 0xCF, 0x28, 0x22, 0x7E, 0x07, 0xE1, 0x03, 0x2D, 0xAB, 0x7D, 0x0E, 0x09, 0xA1, 0x5F, 0x13, 0x41, 0x48, 0xC1, 0x20, 0x09, 0xDA, + 0x53, 0x6B, 0x22, 0xCC, 0x62, 0x47, 0x4E, 0x69, 0xCC, 0x15, 0x54, 0xC0, 0x81, 0x4D, 0x6C, 0xA0, 0xB7, 0x22, 0x59, 0x43, 0x83, 0xA9, 0xD0, 0xA2, 0xC7, 0x7F, 0xD3, 0x65, 0xA5, 0x54, 0x42, 0x95, + 0xFB, 0xB9, 0x73, 0xF9, 0x1E, 0xA5, 0x64, 0x90, 0xD6, 0xCA, 0x68, 0x76, 0x49, 0x7B, 0x98, 0xB3, 0xCB, 0x12, 0x41, 0x7C, 0x25, 0x7B, 0x6D, 0x0F, 0x71, 0x83, 0xDB, 0xB6, 0x9E, 0x33, 0x07, 0x5B, + 0xEB, 0x01, 0x17, 0xB6, 0x91, 0x4C, 0x69, 0xBA, 0x38, 0x34, 0x94, 0x22, 0xF2, 0xF4, 0x33, 0x64, 0x82, 0x2A, 0x25, 0x70, 0x95, 0x2D, 0xD5, 0x07, 0x7B, 0x90, 0x75, 0x5F, 0x15, 0x74, 0x11, 0x5B, + 0x8E, 0x22, 0x14, 0x27, 0x58, 0x59, 0x61, 0x91, 0x3A, 0x9B, 0xFA, 0x05, 0x02, 0xB5, 0xD7, 0x9A, 0xB7, 0x81, 0x17, 0x44, 0xE6, 0x56, 0x3C, 0x5B, 0x62, 0xC5, 0xCC, 0x4E, 0x93, 0x23, 0x9A, 0x0A, + 0x8C, 0xC6, 0x0F, 0xE8, 0x48, 0xF8, 0x4A, 0x95, 0xF5, 0x90, 0x25, 0x99, 0xB5, 0x4A, 0x06, 0x62, 0x93, 0xA2, 0x02, 0x1D, 0xA1, 0x96, 0x76, 0x6C, 0x17, 0xC7, 0xE8, 0x63, 0xAF, 0x79, 0x0C, 0x27, + 0x0B, 0x21, 0x6A, 0x25, 0x13, 0x8D, 0xDA, 0x0C, 0x81, 0x26, 0xE0, 0x93, 0x77, 0x87, 0x98, 0x59, 0xDB, 0x35, 0x8F, 0x9B, 0x82, 0xB7, 0xC8, 0xA6, 0x79, 0x2A, 0xCE, 0xE9, 0x2A, 0x4C, 0xBD, 0xE3, + 0xCE, 0xDD, 0x45, 0x00, 0xAC, 0xBC, 0x55, 0x5C, 0x28, 0x8E, 0xFF, 0x97, 0x95, 0x26, 0x5B, 0x90, 0x05, 0x35, 0x1C, 0x52, 0xE2, 0x65, 0x35, 0x54, 0xAB, 0xAA, 0xF8, 0x72, 0xDF, 0x95, 0xCA, 0x7F, + 0x79, 0x59, 0x03, 0xF0, 0xB0, 0xA1, 0x82, 0xB1, 0x8A, 0xEB, 0x04, 0x75, 0xB2, 0x9F, 0x6E, 0x3A, 0xBF, 0x4C, 0x22, 0x50, 0xFE, 0x7B, 0x84, 0x2A, 0x73, 0x65, 0x50, 0x16, 0xA8, 0xFC, 0x72, 0x9F, + 0x39, 0x05, 0x07, 0xAC, 0xA9, 0x36, 0x82, 0x5A, 0x98, 0xB3, 0xA3, 0x2E, 0x6B, 0x25, 0x54, 0xCE, 0x95, 0x28, 0x94, 0x1A, 0x3B, 0xB8, 0xC9, 0x09, 0x96, 0x00, 0x8D, 0x74, 0xFB, 0xCD, 0x02, 0x0A, + 0x02, 0xE7, 0x06, 0xA6, 0xDE, 0x7B, 0x02, 0xAF, 0x40, 0x4C, 0x10, 0xDB, 0x00, 0xFA, 0xEC, 0x02, 0xD3, 0xEA, 0xA6, 0xD9, 0x56, 0x1A, 0x15, 0x65, 0xA7, 0xB0, 0x5C, 0x63, 0x66, 0xD0, 0x9D, 0xA7, + 0xA5, 0x37, 0xF2, 0x0C, 0x7B, 0x28, 0x59, 0xA8, 0x3E, 0x02, 0x9E, 0x13, 0xA9, 0xBD, 0x28, 0x91, 0x57, 0xC5, 0xB7, 0x4C, 0x84, 0xEA, 0xA3, 0x07, 0x75, 0x3D, 0x43, 0x12, 0x02, 0xA3, 0xD9, 0xB6, + 0x16, 0x22, 0x18, 0xBE, 0xC5, 0x34, 0x69, 0x45, 0xBF, 0xEF, 0x55, 0xB6, 0x24, 0xC5, 0xC6, 0xE3, 0x73, 0x35, 0x9B, 0xB1, 0xC4, 0x79, 0x95, 0x2B, 0xBA, 0xBA, 0x4D, 0x65, 0x55, 0xC2, 0x76, 0x57, + 0x3E, 0x51, 0x52, 0xB5, 0x53, 0x90, 0x19, 0x99, 0xF6, 0x94, 0x02, 0xD1, 0x50, 0xBE, 0xF7, 0x9D, 0x74, 0xFB, 0x29, 0x53, 0x01, 0x8F, 0xF4, 0x86, 0x66, 0x74, 0x6A, 0xCE, 0x60, 0x78, 0x14, 0xA1, + 0xFA, 0x33, 0x19, 0x57, 0x20, 0xF8, 0x38, 0x78, 0xD3, 0xB5, 0x75, 0xC7, 0x25, 0x74, 0x4A, 0x72, 0x07, 0x0D, 0xD0, 0x44, 0x01, 0x80, 0x42, 0xDA, 0x25, 0x71, 0x4D, 0x17, 0x30, 0x90, 0x32, 0x3A, + 0x51, 0xE6, 0xC0, 0x63, 0xD2, 0x03, 0x88, 0x13, 0x80, 0x91, 0x27, 0x61, 0xFC, 0x34, 0x10, 0x83, 0x90, 0x95, 0xF2, 0x6C, 0x0E, 0x68, 0x7A, 0x00, 0x70, 0x54, 0x95, 0xE1, 0x71, 0xB5, 0x71, 0x51, + 0xAC, 0xE0, 0x49, 0x8E, 0x30, 0xF1, 0x4C, 0xA9, 0xB0, 0x2F, 0x6E, 0x40, 0x83, 0x18, 0x54, 0xC2, 0xE0, 0xAB, 0x1E, 0xCD, 0x0C, 0x21, 0xD8, 0xE4, 0xC7, 0xE6, 0x69, 0xCD, 0x72, 0x82, 0x30, 0xB9, + 0xD1, 0x1F, 0x72, 0xC2, 0x66, 0xE3, 0x44, 0x66, 0xF9, 0xC0, 0x15, 0x9E, 0xF4, 0x24, 0xF8, 0xF3, 0x1D, 0x95, 0xA5, 0x7B, 0xA0, 0xE2, 0x10, 0x54, 0x3C, 0x10, 0xC6, 0x50, 0x3F, 0xB5, 0xC6, 0x3E, + 0xD2, 0x3A, 0xA3, 0x6C, 0xD6, 0xA6, 0xF3, 0x78, 0x26, 0x1B, 0x0B, 0x1E, 0x79, 0x50, 0x9D, 0x8B, 0xEB, 0x36, 0xAA, 0x26, 0x3D, 0xC9, 0x15, 0x45, 0xE5, 0x33, 0x69, 0xDF, 0x26, 0x83, 0x7F, 0x39, + 0x4C, 0x56, 0x77, 0x7C, 0x95, 0xB6, 0x48, 0xBD, 0x1A, 0x72, 0x92, 0x1A, 0xBF, 0x49, 0x56, 0x3F, 0x99, 0xCB, 0x9D, 0x98, 0xEA, 0xB5, 0xC6, 0x66, 0x66, 0xF6, 0xB1, 0x6F, 0x74, 0x02, 0x24, 0x81, + 0xFA, 0x21, 0x4E, 0x61, 0x76, 0x98, 0xD3, 0xBB, 0xD1, 0x3C, 0xB3, 0x08, 0x71, 0x3F, 0xDC, 0xC7, 0xCF, 0xD3, 0x97, 0xB9, 0xCA, 0x39, 0xAF, 0xF4, 0xC7, 0x44, 0xD5, 0x71, 0x5D, 0x58, 0x96, 0x6F, + 0x2C, 0xF9, 0x70, 0x70, 0x15, 0xC8, 0xF3, 0x54, 0x3E, 0xD2, 0x86, 0xA3, 0xD8, 0xD5, 0xCB, 0xF6, 0x4A, 0xCE, 0xDF, 0xC0, 0x29, 0x71, 0xA9, 0x10, 0x72, 0xC6, 0x9D, 0x2E, 0xF4, 0x98, 0x29, 0xF1, + 0x03, 0x7F, 0x05, 0x0C, 0x5B, 0x92, 0x22, 0x98, 0x56, 0xCB, 0x12, 0xB4, 0x56, 0xCC, 0x09, 0x52, 0x82, 0xA6, 0x26, 0x87, 0xEA, 0x38, 0xC9, 0x77, 0x8A, 0xEA, 0x49, 0x1D, 0xFF, 0x06, 0x97, 0x11, + 0xFB, 0xBE, 0x05, 0xE8, 0xCD, 0x9B, 0xF4, 0x4A, 0x8E, 0x71, 0x26, 0x19, 0x57, 0x3E, 0x12, 0xEA, 0xA7, 0xB2, 0x38, 0x29, 0xDC, 0x67, 0x26, 0xBF, 0xE3, 0x3D, 0xA1, 0x36, 0xB8, 0x1E, 0x15, 0x32, + 0x51, 0x50, 0x8F, 0x62, 0x85, 0xBA, 0x15, 0xB2, 0xC1, 0x23, 0x76, 0x77, 0xFE, 0x5B, 0x14, 0xB4, 0xE3, 0x3F, 0x98, 0xC3, 0x26, 0xBC, 0x58, 0xB9, 0xD8, 0xE0, 0x75, 0xA2, 0x5B, 0x94, 0xC8, 0xA2, + 0x32, 0x33, 0x02, 0x9D, 0xCC, 0x78, 0x6B, 0x13, 0x5C, 0x56, 0x16, 0x4B, 0xA3, 0xD1, 0x60, 0xCB, 0xCE, 0xA8, 0x54, 0xB7, 0x97, 0x1F, 0x9C, 0xD7, 0x3A, 0x38, 0x3A, 0xAC, 0x05, 0x0A, 0x30, 0x2A, + 0xD8, 0x3B, 0x3E, 0x3A, 0xB9, 0x02, 0x46, 0xAD, 0x16, 0x0A, 0x32, 0x1D, 0x33, 0x0A, 0xCD, 0xEC, 0x7C, 0xA6, 0x64, 0x3D, 0x7E, 0xC0, 0x1F, 0x91, 0x69, 0x1F, 0x16, 0x32, 0x5B, 0xDF, 0x39, 0x69, + 0x50, 0xB8, 0x8D, 0xAF, 0xE3, 0x69, 0xC6, 0x54, 0xB8, 0x52, 0x05, 0x5C, 0x97, 0x03, 0x62, 0xC6, 0x13, 0x80, 0x46, 0x07, 0x57, 0xC6, 0x58, 0x90, 0xF4, 0xE5, 0x92, 0x22, 0xE4, 0xA4, 0x06, 0x0B, + 0x26, 0xC0, 0xEB, 0xC1, 0x01, 0x97, 0x59, 0x0D, 0xE3, 0xC8, 0xF0, 0x95, 0x5D, 0x65, 0x4B, 0x37, 0x1C, 0xCB, 0x90, 0xAC, 0xA3, 0x71, 0xB2, 0x94, 0x47, 0x6C, 0x16, 0xA4, 0x59, 0x6A, 0x1D, 0xE8, + 0x30, 0x9E, 0x2A, 0x36, 0x12, 0xC6, 0x9B, 0x71, 0x25, 0x31, 0x05, 0x01, 0xE0, 0xC0, 0x49, 0xB8, 0x74, 0x40, 0xD9, 0xA6, 0xD0, 0xEC, 0xB9, 0x99, 0xC9, 0xA0, 0x94, 0x2A, 0xA3, 0x40, 0xF6, 0x03, + 0x65, 0xEA, 0xFD, 0x46, 0x5F, 0xC6, 0x4A, 0x0C, 0x5F, 0x8F, 0x3F, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9D, 0x59, 0xA5, 0x43, 0xD8, 0x20, 0x8C, 0x54, 0xA3, 0x16, 0x65, 0x29, 0xB5, 0x39, 0x22, + }, + .pkcs8_len = 0, + .spki_len = 0, + .secret_len = 32, + .secret = { + 0xed, 0x20, 0x14, 0x0c, 0x05, 0xd7, 0x8b, 0x15, 0xf2, 0xe4, 0x12, 0x67, 0x1a, 0x84, 0x15, 0x42, 0x17, 0xfd, 0x77, 0x61, 0x9a, 0x2c, 0x52, 0x2d, 0x3c, 0x3c, 0xb6, 0x88, 0xcb, 0x34, 0xc6, 0x8b, + }, + .cipher_len = 1088, + .cipher = { + 0xea, 0xdd, 0x5a, 0xda, 0x14, 0xda, 0x57, 0xf0, 0xae, 0xf3, 0x50, 0x5f, 0x1c, 0xaa, 0x64, 0x85, 0xd4, 0x23, 0x8d, 0x99, 0x9a, 0x3e, 0xf4, 0xb0, 0xa5, 0x9a, 0x1c, 0xdb, 0xe0, 0xa2, 0x7e, 0x47, + 0x85, 0x47, 0xa3, 0xa9, 0x9d, 0x2a, 0xb0, 0x9a, 0xc7, 0xd7, 0xc8, 0xf5, 0xae, 0x3d, 0x64, 0x32, 0x04, 0x5c, 0xba, 0x3f, 0xa7, 0x78, 0x34, 0x58, 0x92, 0x54, 0x2b, 0xd8, 0x1c, 0x05, 0xbe, 0xfc, + 0xd2, 0xe5, 0xcc, 0x9a, 0x57, 0x9b, 0xef, 0xb7, 0xc5, 0x8d, 0x02, 0xfb, 0x94, 0xf3, 0x33, 0x92, 0xfe, 0x17, 0xf4, 0xeb, 0xa2, 0xcb, 0x51, 0x0e, 0xc7, 0x4c, 0xc9, 0xd1, 0xd8, 0xa8, 0x7c, 0x10, + 0x66, 0xa4, 0x86, 0x9a, 0x39, 0x83, 0xe6, 0x64, 0xbf, 0xe9, 0xde, 0xa5, 0xae, 0x4f, 0xdf, 0x31, 0x0c, 0x8f, 0x59, 0x81, 0x5a, 0x67, 0x8f, 0xa3, 0x25, 0xf3, 0x69, 0xaf, 0x84, 0xff, 0xeb, 0xc1, + 0xd1, 0x50, 0x43, 0x1f, 0xe3, 0xbd, 0x27, 0x34, 0xf6, 0x36, 0xcf, 0x65, 0x8e, 0x6c, 0x1a, 0x6a, 0x6e, 0x2c, 0xbe, 0x07, 0x1f, 0x9a, 0x7c, 0x26, 0x11, 0x9a, 0xd1, 0x05, 0x09, 0x8e, 0xda, 0x62, + 0x2c, 0xab, 0x8e, 0x17, 0x67, 0x62, 0x10, 0x98, 0x77, 0xd9, 0xae, 0x9d, 0x67, 0x29, 0xd4, 0x4a, 0x58, 0xe7, 0x07, 0xd6, 0xb8, 0xad, 0x6e, 0x69, 0x6a, 0x33, 0xc6, 0x72, 0xda, 0x9d, 0x08, 0xda, + 0x2a, 0x7f, 0x9e, 0x3b, 0xf0, 0x22, 0x18, 0x23, 0x87, 0x22, 0xa4, 0x6b, 0x31, 0xd4, 0x9d, 0xaf, 0xf9, 0xaf, 0x00, 0xa6, 0x36, 0x3c, 0x3a, 0x42, 0x3b, 0x2e, 0x87, 0x3d, 0xef, 0xdd, 0xbc, 0xd9, + 0x69, 0xb7, 0x5a, 0x81, 0x05, 0x3d, 0x9a, 0x97, 0xc0, 0x6d, 0xe2, 0xbf, 0xe3, 0xd0, 0xcf, 0xd3, 0xd3, 0xc7, 0x79, 0x83, 0xb1, 0x8d, 0xbd, 0xe2, 0x3c, 0x07, 0x28, 0x60, 0x4a, 0x71, 0x43, 0x5a, + 0xd4, 0x0d, 0xf1, 0x57, 0x90, 0x96, 0xdd, 0xbe, 0x02, 0xe4, 0x61, 0x22, 0x10, 0xca, 0xa0, 0x34, 0xdc, 0xef, 0xb8, 0xb4, 0xd7, 0xb5, 0xe6, 0xd2, 0xeb, 0xa3, 0x7a, 0x79, 0xfb, 0x61, 0xf3, 0x4b, + 0x5a, 0xf7, 0xd9, 0xb2, 0x7b, 0x13, 0xe4, 0x93, 0x62, 0x22, 0x41, 0x12, 0x49, 0xb7, 0xfb, 0xb6, 0x9e, 0x73, 0x46, 0x1d, 0xaf, 0x4a, 0xa6, 0xf3, 0xe2, 0xc7, 0x39, 0x44, 0xf1, 0x0c, 0xe6, 0x7c, + 0x86, 0xfe, 0xd2, 0x60, 0xbd, 0xa7, 0xb4, 0x0d, 0xb3, 0x9b, 0x1d, 0xe3, 0xc7, 0xd8, 0xf0, 0x9a, 0x77, 0xf3, 0xc8, 0x4b, 0xc6, 0x29, 0x31, 0xd2, 0x28, 0xb2, 0x4a, 0x57, 0x4a, 0xc3, 0xf4, 0xeb, + 0x74, 0x5c, 0xff, 0x7e, 0x03, 0x1a, 0x3f, 0xb2, 0xa0, 0x85, 0x95, 0xc1, 0x53, 0x70, 0xa3, 0xc8, 0x2d, 0xb7, 0xd9, 0xf4, 0x1b, 0xb1, 0xd8, 0xec, 0xc4, 0x29, 0xcf, 0xa3, 0xa6, 0x58, 0x33, 0x01, + 0x6a, 0xb6, 0xea, 0x60, 0xc9, 0x39, 0x0c, 0xfa, 0x1b, 0x65, 0xcc, 0xea, 0xe5, 0x50, 0x94, 0x07, 0x95, 0x38, 0x6e, 0xd2, 0x41, 0x33, 0xfb, 0xae, 0x8b, 0x30, 0x17, 0x50, 0x2a, 0xf3, 0xcf, 0xe9, + 0x51, 0xd7, 0x81, 0xd3, 0x6c, 0xfe, 0xff, 0x85, 0xbf, 0xdf, 0x5a, 0xf0, 0x40, 0xbe, 0x40, 0x65, 0x68, 0x1b, 0x3b, 0x0a, 0x63, 0xc2, 0x74, 0x7f, 0x08, 0x08, 0xcf, 0x3d, 0xa7, 0x25, 0x16, 0x9d, + 0xde, 0xd1, 0x00, 0x3d, 0xa6, 0xcd, 0x5d, 0xe4, 0xcb, 0x04, 0x19, 0x42, 0x93, 0x8d, 0x0a, 0x7f, 0x88, 0x02, 0xd4, 0x8f, 0x2e, 0x3c, 0x6e, 0xeb, 0x45, 0xcd, 0x90, 0xaf, 0x6f, 0xc9, 0xf4, 0x50, + 0x7e, 0x9f, 0x83, 0x80, 0xac, 0x33, 0xca, 0xca, 0x77, 0x51, 0x48, 0x7f, 0x65, 0x50, 0x04, 0x41, 0xd9, 0x20, 0xb9, 0x48, 0x80, 0xa4, 0x97, 0xd0, 0x1c, 0x08, 0x02, 0xbb, 0x08, 0xd7, 0x4c, 0x5d, + 0x4c, 0x6b, 0xf2, 0xd8, 0x65, 0xee, 0x58, 0x22, 0xb3, 0x37, 0x5c, 0x75, 0x5d, 0x1a, 0x5e, 0x3d, 0x32, 0x44, 0xc3, 0x20, 0x51, 0x0a, 0x1e, 0x30, 0x35, 0x77, 0x02, 0xcd, 0x42, 0x52, 0x07, 0x2c, + 0xf8, 0x64, 0x37, 0xf7, 0xa9, 0xde, 0x55, 0x61, 0xc7, 0xe5, 0x9b, 0x94, 0xb9, 0x58, 0x41, 0x00, 0x13, 0x1a, 0xc3, 0x99, 0xf4, 0xc1, 0xeb, 0x19, 0xfb, 0x4b, 0xdf, 0x65, 0xe6, 0x27, 0x85, 0xe9, + 0x7c, 0x19, 0x4b, 0x87, 0x64, 0xcc, 0xf3, 0x2f, 0xd0, 0x5d, 0x80, 0x4c, 0x2e, 0x43, 0x9d, 0xda, 0x2a, 0x10, 0x92, 0x74, 0xfb, 0xff, 0xa8, 0x1a, 0x83, 0x7c, 0x51, 0xb2, 0x6d, 0x15, 0x4f, 0x97, + 0x4b, 0x88, 0x2a, 0x5b, 0x17, 0x4b, 0x30, 0x8f, 0xc4, 0x87, 0x68, 0xd2, 0x22, 0x92, 0x25, 0x32, 0xb1, 0x83, 0xab, 0xdf, 0x6f, 0xbb, 0x0b, 0xc7, 0x49, 0x27, 0x66, 0x97, 0x4d, 0x32, 0x1e, 0xe6, + 0xfb, 0x7c, 0x5f, 0x7b, 0x3e, 0xea, 0x23, 0x78, 0xdc, 0x6d, 0x6b, 0xb4, 0x80, 0x19, 0x25, 0x0b, 0x8d, 0x8d, 0x8d, 0xed, 0xb5, 0x22, 0x42, 0x1a, 0xee, 0xdb, 0x31, 0x86, 0x76, 0x98, 0x2a, 0x80, + 0xe7, 0x96, 0x1e, 0xc4, 0x0e, 0x6d, 0x7f, 0x33, 0x39, 0x69, 0x42, 0x55, 0xba, 0xff, 0x51, 0xbe, 0x3a, 0x7e, 0xa7, 0xd8, 0x79, 0x3a, 0x10, 0x9b, 0xe3, 0xae, 0x44, 0x23, 0xbf, 0x08, 0x2e, 0x20, + 0x6a, 0x57, 0x3b, 0x4f, 0x0f, 0x93, 0xfc, 0x16, 0xdd, 0xe8, 0x1b, 0xd5, 0xdc, 0x58, 0x3f, 0x52, 0x8c, 0x08, 0xa0, 0xa9, 0xab, 0x8e, 0x6c, 0xd5, 0x24, 0xe2, 0x97, 0xc9, 0xcf, 0x0f, 0x43, 0xc3, + 0x44, 0x91, 0x38, 0x30, 0xec, 0xb1, 0x6f, 0x91, 0x44, 0x14, 0x77, 0xba, 0x78, 0x2e, 0xdd, 0x4e, 0x73, 0xe7, 0x32, 0x97, 0x9d, 0x3a, 0x66, 0x4e, 0xb9, 0x9e, 0xa5, 0xd2, 0x4b, 0x6c, 0x84, 0xaa, + 0x69, 0xf3, 0x77, 0xcb, 0x0c, 0xad, 0x5a, 0xe4, 0xe6, 0x41, 0xe3, 0x8b, 0x19, 0x7a, 0x09, 0x94, 0xd5, 0x8b, 0x23, 0x87, 0xe9, 0x17, 0x60, 0xe9, 0xb6, 0xfe, 0xbc, 0xb4, 0x45, 0xcf, 0x85, 0xbb, + 0xa2, 0x4a, 0x94, 0xcd, 0xa7, 0x5e, 0x33, 0x86, 0x74, 0x42, 0x82, 0x49, 0xfe, 0x6d, 0xe4, 0x69, 0x26, 0x01, 0xd1, 0xea, 0xe0, 0xea, 0x02, 0x1d, 0x9b, 0xc8, 0x07, 0x7b, 0xe8, 0x66, 0x5d, 0x07, + 0x37, 0x74, 0x8f, 0xa3, 0x0f, 0xcf, 0x80, 0xf7, 0xe4, 0x82, 0x58, 0x46, 0x74, 0xf6, 0x33, 0xa5, 0x00, 0x6a, 0x53, 0x82, 0x67, 0x62, 0x7f, 0xd9, 0x18, 0x54, 0xe0, 0x87, 0x12, 0x68, 0xa6, 0xb0, + 0xb0, 0x5d, 0xd5, 0x14, 0x95, 0x13, 0x5d, 0xef, 0xb9, 0x37, 0x6e, 0x9b, 0x84, 0x1b, 0x64, 0xe5, 0xdb, 0xf4, 0x3c, 0xe6, 0xc7, 0x4b, 0xcf, 0x3a, 0xe1, 0xfc, 0x42, 0x7e, 0x81, 0x0b, 0x7c, 0xbf, + 0x69, 0x57, 0xdb, 0xf9, 0x04, 0x69, 0x0e, 0x87, 0x84, 0x25, 0x43, 0x89, 0x7d, 0xe7, 0x8f, 0x13, 0xd0, 0x8d, 0x92, 0xeb, 0xd2, 0x7f, 0xb2, 0xcf, 0xcc, 0x0c, 0x76, 0x54, 0x30, 0x58, 0x90, 0x57, + 0xb1, 0x6b, 0x15, 0xf2, 0x07, 0xca, 0x1e, 0x6f, 0x08, 0xd5, 0x26, 0x16, 0xdd, 0x57, 0xad, 0x43, 0xef, 0xea, 0x6f, 0xdd, 0xaa, 0xea, 0x18, 0xd3, 0x37, 0x31, 0xfa, 0xc7, 0xec, 0xaa, 0xe9, 0x50, + 0xe1, 0xdf, 0x3c, 0x5a, 0x4e, 0x6f, 0xcb, 0x22, 0x3d, 0xf5, 0xe8, 0x6b, 0x48, 0x7f, 0xd7, 0x09, 0x2d, 0x08, 0x22, 0xef, 0xfa, 0xec, 0x82, 0xc4, 0xbe, 0xc1, 0x0c, 0x60, 0x0f, 0xdb, 0x90, 0xe7, + 0x74, 0x82, 0x91, 0x1b, 0x15, 0x95, 0x27, 0x77, 0x38, 0x84, 0x14, 0x09, 0xd0, 0xf8, 0xf1, 0x13, 0x19, 0x1d, 0x47, 0xf5, 0xe5, 0x6c, 0x11, 0x5a, 0x05, 0xde, 0xa7, 0x59, 0xaa, 0x6f, 0xb1, 0xd0, + 0x47, 0xf9, 0xfc, 0xa4, 0xed, 0x51, 0x9e, 0xa5, 0xd2, 0x1f, 0xe3, 0xba, 0x5b, 0x94, 0x34, 0xfe, 0xa1, 0x28, 0x3d, 0xfa, 0xd6, 0x3d, 0x01, 0x58, 0x9b, 0x0e, 0xb6, 0x1f, 0x24, 0x43, 0x51, 0xd0, + 0x33, 0x41, 0xdc, 0xd4, 0xdf, 0x62, 0x26, 0x5a, 0xfc, 0xae, 0xc6, 0x67, 0x6a, 0x87, 0x7d, 0x5c, 0xac, 0xb3, 0x59, 0xeb, 0xb5, 0x31, 0x96, 0x10, 0xdd, 0x44, 0x7d, 0xa9, 0x7e, 0x95, 0x0b, 0x0c, + }, + }, + { + .name = "Kyber Round 2, 786 KAT 1 (PKCS#8/SPKI)", + .version = 0, + .keyform = 0, + .pk_len = 0, + .sk_len = 0, + .pkcs8_len = 3697, + .pkcs8 = { + 0x30, 0x82, 0x0e, 0x6d, 0x02, 0x01, 0x00, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x05, 0x03, 0x03, 0x05, 0x00, 0x04, 0x82, 0x0e, 0x55, 0x30, 0x82, 0x0e, 0x51, + 0x02, 0x01, 0x00, 0x03, 0x82, 0x09, 0x61, 0x00, 0x07, 0x63, 0x8f, 0xb6, 0x98, 0x68, 0xf3, 0xd3, 0x20, 0xe5, 0x86, 0x2b, 0xd9, 0x69, 0x33, 0xfe, 0xb3, 0x11, 0xb3, 0x62, 0x09, 0x3c, 0x9b, 0x5d, + 0x50, 0x17, 0x0b, 0xce, 0xd4, 0x3f, 0x1b, 0x53, 0x6d, 0x9a, 0x20, 0x4b, 0xb1, 0xf2, 0x26, 0x95, 0x95, 0x0b, 0xa1, 0xf2, 0xa9, 0xe8, 0xeb, 0x82, 0x8b, 0x28, 0x44, 0x88, 0x76, 0x0b, 0x3f, 0xc8, + 0x4f, 0xab, 0xa0, 0x42, 0x75, 0xd5, 0x62, 0x8e, 0x39, 0xc5, 0xb2, 0x47, 0x13, 0x74, 0x28, 0x3c, 0x50, 0x32, 0x99, 0xc0, 0xab, 0x49, 0xb6, 0x6b, 0x8b, 0xbb, 0x56, 0xa4, 0x18, 0x66, 0x24, 0xf9, + 0x19, 0xa2, 0xba, 0x59, 0xbb, 0x08, 0xd8, 0x55, 0x18, 0x80, 0xc2, 0xbe, 0xfc, 0x4f, 0x87, 0xf2, 0x5f, 0x59, 0xab, 0x58, 0x7a, 0x79, 0xc3, 0x27, 0xd7, 0x92, 0xd5, 0x4c, 0x97, 0x4a, 0x69, 0x26, + 0x2f, 0xf8, 0xa7, 0x89, 0x38, 0x28, 0x9e, 0x9a, 0x87, 0xb6, 0x88, 0xb0, 0x83, 0xe0, 0x59, 0x5f, 0xe2, 0x18, 0xb6, 0xbb, 0x15, 0x05, 0x94, 0x1c, 0xe2, 0xe8, 0x1a, 0x5a, 0x64, 0xc5, 0xaa, 0xc6, + 0x04, 0x17, 0x25, 0x69, 0x85, 0x34, 0x9e, 0xe4, 0x7a, 0x52, 0x42, 0x0a, 0x5f, 0x97, 0x47, 0x7b, 0x72, 0x36, 0xac, 0x76, 0xbc, 0x70, 0xe8, 0x28, 0x87, 0x29, 0x28, 0x7e, 0xe3, 0xe3, 0x4a, 0x3d, + 0xbc, 0x36, 0x83, 0xc0, 0xb7, 0xb1, 0x00, 0x29, 0xfc, 0x20, 0x34, 0x18, 0x53, 0x7e, 0x74, 0x66, 0xba, 0x63, 0x85, 0xa8, 0xff, 0x30, 0x1e, 0xe1, 0x27, 0x08, 0xf8, 0x2a, 0xaa, 0x1e, 0x38, 0x0f, + 0xc7, 0xa8, 0x8f, 0x8f, 0x20, 0x5a, 0xb7, 0xe8, 0x8d, 0x7e, 0x95, 0x95, 0x2a, 0x55, 0xba, 0x20, 0xd0, 0x9b, 0x79, 0xa4, 0x71, 0x41, 0xd6, 0x2b, 0xf6, 0xeb, 0x7d, 0xd3, 0x07, 0xb0, 0x8e, 0xca, + 0x13, 0xa5, 0xbc, 0x5f, 0x6b, 0x68, 0x58, 0x1c, 0x68, 0x65, 0xb2, 0x7b, 0xbc, 0xdd, 0xab, 0x14, 0x2f, 0x4b, 0x2c, 0xbf, 0xf4, 0x88, 0xc8, 0xa2, 0x27, 0x05, 0xfa, 0xa9, 0x8a, 0x2b, 0x9e, 0xea, + 0x35, 0x30, 0xc7, 0x66, 0x62, 0x33, 0x5c, 0xc7, 0xea, 0x3a, 0x00, 0x77, 0x77, 0x25, 0xeb, 0xcc, 0xcd, 0x2a, 0x46, 0x36, 0xb2, 0xd9, 0x12, 0x2f, 0xf3, 0xab, 0x77, 0x12, 0x3c, 0xe0, 0x88, 0x3c, + 0x19, 0x11, 0x11, 0x5e, 0x50, 0xc9, 0xe8, 0xa9, 0x41, 0x94, 0xe4, 0x8d, 0xd0, 0xd0, 0x9c, 0xff, 0xb3, 0xad, 0xcd, 0x2c, 0x1e, 0x92, 0x43, 0x09, 0x03, 0xd0, 0x7a, 0xdb, 0xf0, 0x05, 0x32, 0x03, + 0x15, 0x75, 0xaa, 0x7f, 0x9e, 0x7b, 0x5a, 0x1f, 0x33, 0x62, 0xde, 0xc9, 0x36, 0xd4, 0x04, 0x3c, 0x05, 0xf2, 0x47, 0x6c, 0x07, 0x57, 0x8b, 0xc9, 0xcb, 0xaf, 0x2a, 0xb4, 0xe3, 0x82, 0x72, 0x7a, + 0xd4, 0x16, 0x86, 0xa9, 0x6b, 0x25, 0x48, 0x82, 0x0b, 0xb0, 0x3b, 0x32, 0xf1, 0x1b, 0x28, 0x11, 0xad, 0x62, 0xf4, 0x89, 0xe9, 0x51, 0x63, 0x2a, 0xba, 0x0d, 0x1d, 0xf8, 0x96, 0x80, 0xcc, 0x8a, + 0x8b, 0x53, 0xb4, 0x81, 0xd9, 0x2a, 0x68, 0xd7, 0x0b, 0x4e, 0xa1, 0xc3, 0xa6, 0xa5, 0x61, 0xc0, 0x69, 0x28, 0x82, 0xb5, 0xca, 0x8c, 0xc9, 0x42, 0xa8, 0xd4, 0x95, 0xaf, 0xcb, 0x06, 0xde, 0x89, + 0x49, 0x8f, 0xb9, 0x35, 0xb7, 0x75, 0x90, 0x8f, 0xe7, 0xa0, 0x3e, 0x32, 0x4d, 0x54, 0xcc, 0x19, 0xd4, 0xe1, 0xaa, 0xbd, 0x35, 0x93, 0xb3, 0x8b, 0x19, 0xee, 0x13, 0x88, 0xfe, 0x49, 0x2b, 0x43, + 0x12, 0x7e, 0x5a, 0x50, 0x42, 0x53, 0x78, 0x6a, 0x0d, 0x69, 0xad, 0x32, 0x60, 0x1c, 0x28, 0xe2, 0xc8, 0x85, 0x04, 0xa5, 0xba, 0x59, 0x97, 0x06, 0x02, 0x3a, 0x61, 0x36, 0x3e, 0x17, 0xc6, 0xb9, + 0xbb, 0x59, 0xbd, 0xc6, 0x97, 0x45, 0x2c, 0xd0, 0x59, 0x45, 0x19, 0x83, 0xd7, 0x38, 0xca, 0x3f, 0xd0, 0x34, 0xe3, 0xf5, 0x98, 0x88, 0x54, 0xca, 0x05, 0x03, 0x1d, 0xb0, 0x96, 0x11, 0x49, 0x89, + 0x88, 0x19, 0x7c, 0x6b, 0x30, 0xd2, 0x58, 0xdf, 0xe2, 0x62, 0x65, 0x54, 0x1c, 0x89, 0xa4, 0xb3, 0x1d, 0x68, 0x64, 0xe9, 0x38, 0x9b, 0x03, 0xcb, 0x74, 0xf7, 0xec, 0x43, 0x23, 0xfb, 0x94, 0x21, + 0xa4, 0xb9, 0x79, 0x0a, 0x26, 0xd1, 0x7b, 0x03, 0x98, 0xa2, 0x67, 0x67, 0x35, 0x09, 0x09, 0xf8, 0x4d, 0x57, 0xb6, 0x69, 0x4d, 0xf8, 0x30, 0x66, 0x4c, 0xa8, 0xb3, 0xc3, 0xc0, 0x3e, 0xd2, 0xae, + 0x67, 0xb8, 0x90, 0x06, 0x86, 0x8a, 0x68, 0x52, 0x7c, 0xcd, 0x66, 0x64, 0x59, 0xab, 0x7f, 0x05, 0x66, 0x71, 0x00, 0x0c, 0x61, 0x64, 0xd3, 0xa7, 0xf2, 0x66, 0xa1, 0x4d, 0x97, 0xcb, 0xd7, 0x00, + 0x4d, 0x6c, 0x92, 0xca, 0xca, 0x77, 0x0b, 0x84, 0x4a, 0x4f, 0xa9, 0xb1, 0x82, 0xe7, 0xb1, 0x8c, 0xa8, 0x85, 0x08, 0x2a, 0xc5, 0x64, 0x6f, 0xcb, 0x4a, 0x14, 0xe1, 0x68, 0x5f, 0xeb, 0x0c, 0x9c, + 0xe3, 0x37, 0x2a, 0xb9, 0x53, 0x65, 0xc0, 0x4f, 0xd8, 0x30, 0x84, 0xf8, 0x0a, 0x23, 0xff, 0x10, 0xa0, 0x5b, 0xf1, 0x5f, 0x7f, 0xa5, 0xac, 0xc6, 0xc0, 0xcb, 0x46, 0x2c, 0x33, 0xca, 0x52, 0x4f, + 0xa6, 0xb8, 0xbb, 0x35, 0x90, 0x43, 0xba, 0x68, 0x60, 0x9e, 0xaa, 0x25, 0x36, 0xe8, 0x1d, 0x08, 0x46, 0x3b, 0x19, 0x65, 0x3b, 0x54, 0x35, 0xba, 0x94, 0x6c, 0x9a, 0xdd, 0xeb, 0x20, 0x2b, 0x04, + 0xb0, 0x31, 0xcc, 0x96, 0x0d, 0xcc, 0x12, 0xe4, 0x51, 0x8d, 0x42, 0x8b, 0x32, 0xb2, 0x57, 0xa4, 0xfc, 0x73, 0x13, 0xd3, 0xa7, 0x98, 0x0d, 0x80, 0x08, 0x2e, 0x93, 0x4f, 0x9d, 0x95, 0xc3, 0x2b, + 0x0a, 0x01, 0x91, 0xa2, 0x36, 0x04, 0x38, 0x4d, 0xd9, 0xe0, 0x79, 0xbb, 0xba, 0xa2, 0x66, 0xd1, 0x4c, 0x3f, 0x75, 0x6b, 0x9f, 0x21, 0x33, 0x10, 0x74, 0x33, 0xa4, 0xe8, 0x3f, 0xa7, 0x18, 0x72, + 0x82, 0xa8, 0x09, 0x20, 0x3a, 0x4f, 0xaf, 0x84, 0x18, 0x51, 0x83, 0x3d, 0x12, 0x1a, 0xc3, 0x83, 0x84, 0x3a, 0x5e, 0x55, 0xbc, 0x23, 0x81, 0x42, 0x5e, 0x16, 0xc7, 0xdb, 0x4c, 0xc9, 0xab, 0x5c, + 0x1b, 0x0d, 0x91, 0xa4, 0x7e, 0x2b, 0x8d, 0xe0, 0xe5, 0x82, 0xc8, 0x6b, 0x6b, 0x0d, 0x90, 0x7b, 0xb3, 0x60, 0xb9, 0x7f, 0x40, 0xab, 0x5d, 0x03, 0x8f, 0x6b, 0x75, 0xc8, 0x14, 0xb2, 0x7d, 0x9b, + 0x96, 0x8d, 0x41, 0x98, 0x32, 0xbc, 0x8c, 0x2b, 0xee, 0x60, 0x5e, 0xf6, 0xe5, 0x05, 0x9d, 0x33, 0x10, 0x0d, 0x90, 0x48, 0x5d, 0x37, 0x84, 0x50, 0x01, 0x42, 0x21, 0x73, 0x6c, 0x07, 0x40, 0x7c, + 0xac, 0x26, 0x04, 0x08, 0xaa, 0x64, 0x92, 0x66, 0x19, 0x78, 0x8b, 0x86, 0x01, 0xc2, 0xa7, 0x52, 0xd1, 0xa6, 0xcb, 0xf8, 0x20, 0xd7, 0xc7, 0xa0, 0x47, 0x16, 0x20, 0x32, 0x25, 0xb3, 0x89, 0x5b, + 0x93, 0x42, 0xd1, 0x47, 0xa8, 0x18, 0x5c, 0xfc, 0x1b, 0xb6, 0x5b, 0xa0, 0x6b, 0x41, 0x42, 0x33, 0x99, 0x03, 0xc0, 0xac, 0x46, 0x51, 0x38, 0x5b, 0x45, 0xd9, 0x8a, 0x8b, 0x19, 0xd2, 0x8c, 0xd6, + 0xba, 0xb0, 0x88, 0x78, 0x7f, 0x7e, 0xe1, 0xb1, 0x24, 0x61, 0x76, 0x6b, 0x43, 0xcb, 0xcc, 0xb9, 0x64, 0x34, 0x42, 0x7d, 0x93, 0xc0, 0x65, 0x55, 0x06, 0x88, 0xf6, 0x94, 0x8e, 0xd1, 0xb5, 0x47, + 0x5a, 0x42, 0x5f, 0x1b, 0x85, 0x20, 0x9d, 0x06, 0x1c, 0x08, 0xb5, 0x6c, 0x1c, 0xc0, 0x69, 0xf6, 0xc0, 0xa7, 0xc6, 0xf2, 0x93, 0x58, 0xca, 0xb9, 0x11, 0x08, 0x77, 0x32, 0xa6, 0x49, 0xd2, 0x7c, + 0x9b, 0x98, 0xf9, 0xa4, 0x88, 0x79, 0x38, 0x7d, 0x9b, 0x00, 0xc2, 0x59, 0x59, 0xa7, 0x16, 0x54, 0xd6, 0xf6, 0xa9, 0x46, 0x16, 0x45, 0x13, 0xe4, 0x7a, 0x75, 0xd0, 0x05, 0x98, 0x6c, 0x23, 0x63, + 0xc0, 0x9f, 0x6b, 0x53, 0x7e, 0xca, 0x78, 0xb9, 0x30, 0x3a, 0x5f, 0xa4, 0x57, 0x60, 0x8a, 0x58, 0x6a, 0x65, 0x3a, 0x34, 0x7d, 0xb0, 0x4d, 0xfc, 0xc1, 0x91, 0x75, 0xb3, 0xa3, 0x01, 0x17, 0x25, + 0x36, 0x06, 0x2a, 0x65, 0x8a, 0x95, 0x27, 0x75, 0x70, 0xc8, 0x85, 0x2c, 0xa8, 0x97, 0x3f, 0x4a, 0xe1, 0x23, 0xa3, 0x34, 0x04, 0x7d, 0xd7, 0x11, 0xc8, 0x92, 0x7a, 0x63, 0x4a, 0x03, 0x38, 0x8a, + 0x52, 0x7b, 0x03, 0x4b, 0xf7, 0xa8, 0x17, 0x0f, 0xa7, 0x02, 0xc1, 0xf7, 0xc2, 0x3e, 0xc3, 0x2d, 0x18, 0xa2, 0x37, 0x48, 0x90, 0xbe, 0x9c, 0x78, 0x7a, 0x94, 0x09, 0xc8, 0x2d, 0x19, 0x2c, 0x4b, + 0xb7, 0x05, 0xa2, 0xf9, 0x96, 0xce, 0x40, 0x5d, 0xa0, 0xb7, 0x1f, 0x67, 0xc6, 0xce, 0xc0, 0xd3, 0x56, 0x86, 0xd5, 0x13, 0x42, 0x34, 0x32, 0xe5, 0x12, 0xac, 0x40, 0x44, 0x55, 0x7e, 0x86, 0x8a, + 0x62, 0x48, 0x00, 0x10, 0x9a, 0x33, 0x55, 0xf9, 0x8f, 0x15, 0x14, 0x44, 0xe2, 0x85, 0x2e, 0x27, 0xea, 0x6e, 0xdb, 0x19, 0x92, 0xca, 0xd3, 0x97, 0x3c, 0x3a, 0x6f, 0xf7, 0x9a, 0x5a, 0x04, 0x9a, + 0x25, 0x9e, 0xb5, 0x41, 0x5a, 0xa2, 0xa2, 0x62, 0x45, 0x6e, 0xc9, 0x49, 0x5b, 0xbb, 0x52, 0x00, 0xd8, 0xd3, 0x16, 0x3a, 0x5b, 0x10, 0x22, 0x62, 0x92, 0xec, 0xa0, 0x10, 0x21, 0x38, 0x9d, 0xa3, + 0x78, 0x81, 0xe2, 0x76, 0x30, 0x65, 0x50, 0xc6, 0xef, 0xb6, 0x44, 0x0e, 0xc5, 0x1a, 0x2f, 0x73, 0x48, 0x34, 0x9b, 0x85, 0x1c, 0xd4, 0xaa, 0x01, 0x75, 0xa0, 0x55, 0x02, 0x13, 0xc4, 0x79, 0x1d, + 0x91, 0x01, 0x12, 0x20, 0x82, 0x4b, 0x2b, 0x61, 0x65, 0x08, 0x13, 0xad, 0xfd, 0x2c, 0xb1, 0x05, 0x38, 0xbf, 0xab, 0x0a, 0x72, 0x6f, 0x81, 0x12, 0x9e, 0xd2, 0xc0, 0xf0, 0x6a, 0x16, 0xb7, 0x01, + 0x09, 0x0b, 0xf0, 0x48, 0xc5, 0xa4, 0x01, 0x26, 0xd5, 0x72, 0xfc, 0xd4, 0x7a, 0xa1, 0x21, 0x8f, 0xb0, 0x15, 0x47, 0xd1, 0x50, 0x79, 0x2d, 0x23, 0x16, 0xcb, 0x32, 0x0d, 0x51, 0x44, 0xba, 0x35, + 0x08, 0xa1, 0xeb, 0xbb, 0x5a, 0xc1, 0xc2, 0x29, 0x13, 0xe8, 0x29, 0x5f, 0xab, 0x59, 0xbf, 0x58, 0x37, 0xa7, 0x78, 0xcf, 0x28, 0x22, 0x7e, 0x07, 0xe1, 0x03, 0x2d, 0xab, 0x7d, 0x0e, 0x09, 0xa1, + 0x5f, 0x13, 0x41, 0x48, 0xc1, 0x20, 0x09, 0xda, 0x53, 0x6b, 0x22, 0xcc, 0x62, 0x47, 0x4e, 0x69, 0xcc, 0x15, 0x54, 0xc0, 0x81, 0x4d, 0x6c, 0xa0, 0xb7, 0x22, 0x59, 0x43, 0x83, 0xa9, 0xd0, 0xa2, + 0xc7, 0x7f, 0xd3, 0x65, 0xa5, 0x54, 0x42, 0x95, 0xfb, 0xb9, 0x73, 0xf9, 0x1e, 0xa5, 0x64, 0x90, 0xd6, 0xca, 0x68, 0x76, 0x49, 0x7b, 0x98, 0xb3, 0xcb, 0x12, 0x41, 0x7c, 0x25, 0x7b, 0x6d, 0x0f, + 0x71, 0x83, 0xdb, 0xb6, 0x9e, 0x33, 0x07, 0x5b, 0xeb, 0x01, 0x17, 0xb6, 0x91, 0x4c, 0x69, 0xba, 0x38, 0x34, 0x94, 0x22, 0xf2, 0xf4, 0x33, 0x64, 0x82, 0x2a, 0x25, 0x70, 0x95, 0x2d, 0xd5, 0x07, + 0x7b, 0x90, 0x75, 0x5f, 0x15, 0x74, 0x11, 0x5b, 0x8e, 0x22, 0x14, 0x27, 0x58, 0x59, 0x61, 0x91, 0x3a, 0x9b, 0xfa, 0x05, 0x02, 0xb5, 0xd7, 0x9a, 0xb7, 0x81, 0x17, 0x44, 0xe6, 0x56, 0x3c, 0x5b, + 0x62, 0xc5, 0xcc, 0x4e, 0x93, 0x23, 0x9a, 0x0a, 0x8c, 0xc6, 0x0f, 0xe8, 0x48, 0xf8, 0x4a, 0x95, 0xf5, 0x90, 0x25, 0x99, 0xb5, 0x4a, 0x06, 0x62, 0x93, 0xa2, 0x02, 0x1d, 0xa1, 0x96, 0x76, 0x6c, + 0x17, 0xc7, 0xe8, 0x63, 0xaf, 0x79, 0x0c, 0x27, 0x0b, 0x21, 0x6a, 0x25, 0x13, 0x8d, 0xda, 0x0c, 0x81, 0x26, 0xe0, 0x93, 0x77, 0x87, 0x98, 0x59, 0xdb, 0x35, 0x8f, 0x9b, 0x82, 0xb7, 0xc8, 0xa6, + 0x79, 0x2a, 0xce, 0xe9, 0x2a, 0x4c, 0xbd, 0xe3, 0xce, 0xdd, 0x45, 0x00, 0xac, 0xbc, 0x55, 0x5c, 0x28, 0x8e, 0xff, 0x97, 0x95, 0x26, 0x5b, 0x90, 0x05, 0x35, 0x1c, 0x52, 0xe2, 0x65, 0x35, 0x54, + 0xab, 0xaa, 0xf8, 0x72, 0xdf, 0x95, 0xca, 0x7f, 0x79, 0x59, 0x03, 0xf0, 0xb0, 0xa1, 0x82, 0xb1, 0x8a, 0xeb, 0x04, 0x75, 0xb2, 0x9f, 0x6e, 0x3a, 0xbf, 0x4c, 0x22, 0x50, 0xfe, 0x7b, 0x84, 0x2a, + 0x73, 0x65, 0x50, 0x16, 0xa8, 0xfc, 0x72, 0x9f, 0x39, 0x05, 0x07, 0xac, 0xa9, 0x36, 0x82, 0x5a, 0x98, 0xb3, 0xa3, 0x2e, 0x6b, 0x25, 0x54, 0xce, 0x95, 0x28, 0x94, 0x1a, 0x3b, 0xb8, 0xc9, 0x09, + 0x96, 0x00, 0x8d, 0x74, 0xfb, 0xcd, 0x02, 0x0a, 0x02, 0xe7, 0x06, 0xa6, 0xde, 0x7b, 0x02, 0xaf, 0x40, 0x4c, 0x10, 0xdb, 0x00, 0xfa, 0xec, 0x02, 0xd3, 0xea, 0xa6, 0xd9, 0x56, 0x1a, 0x15, 0x65, + 0xa7, 0xb0, 0x5c, 0x63, 0x66, 0xd0, 0x9d, 0xa7, 0xa5, 0x37, 0xf2, 0x0c, 0x7b, 0x28, 0x59, 0xa8, 0x3e, 0x02, 0x9e, 0x13, 0xa9, 0xbd, 0x28, 0x91, 0x57, 0xc5, 0xb7, 0x4c, 0x84, 0xea, 0xa3, 0x07, + 0x75, 0x3d, 0x43, 0x12, 0x02, 0xa3, 0xd9, 0xb6, 0x16, 0x22, 0x18, 0xbe, 0xc5, 0x34, 0x69, 0x45, 0xbf, 0xef, 0x55, 0xb6, 0x24, 0xc5, 0xc6, 0xe3, 0x73, 0x35, 0x9b, 0xb1, 0xc4, 0x79, 0x95, 0x2b, + 0xba, 0xba, 0x4d, 0x65, 0x55, 0xc2, 0x76, 0x57, 0x3e, 0x51, 0x52, 0xb5, 0x53, 0x90, 0x19, 0x99, 0xf6, 0x94, 0x02, 0xd1, 0x50, 0xbe, 0xf7, 0x9d, 0x74, 0xfb, 0x29, 0x53, 0x01, 0x8f, 0xf4, 0x86, + 0x66, 0x74, 0x6a, 0xce, 0x60, 0x78, 0x14, 0xa1, 0xfa, 0x33, 0x19, 0x57, 0x20, 0xf8, 0x38, 0x78, 0xd3, 0xb5, 0x75, 0xc7, 0x25, 0x74, 0x4a, 0x72, 0x07, 0x0d, 0xd0, 0x44, 0x01, 0x80, 0x42, 0xda, + 0x25, 0x71, 0x4d, 0x17, 0x30, 0x90, 0x32, 0x3a, 0x51, 0xe6, 0xc0, 0x63, 0xd2, 0x03, 0x88, 0x13, 0x80, 0x91, 0x27, 0x61, 0xfc, 0x34, 0x10, 0x83, 0x90, 0x95, 0xf2, 0x6c, 0x0e, 0x68, 0x7a, 0x00, + 0x70, 0x54, 0x95, 0xe1, 0x71, 0xb5, 0x71, 0x51, 0xac, 0xe0, 0x49, 0x8e, 0x30, 0xf1, 0x4c, 0xa9, 0xb0, 0x2f, 0x6e, 0x40, 0x83, 0x18, 0x54, 0xc2, 0xe0, 0xab, 0x1e, 0xcd, 0x0c, 0x21, 0xd8, 0xe4, + 0xc7, 0xe6, 0x69, 0xcd, 0x72, 0x82, 0x30, 0xb9, 0xd1, 0x1f, 0x72, 0xc2, 0x66, 0xe3, 0x44, 0x66, 0xf9, 0xc0, 0x15, 0x9e, 0xf4, 0x24, 0xf8, 0xf3, 0x1d, 0x95, 0xa5, 0x7b, 0xa0, 0xe2, 0x10, 0x54, + 0x3c, 0x10, 0xc6, 0x50, 0x3f, 0xb5, 0xc6, 0x3e, 0xd2, 0x3a, 0xa3, 0x6c, 0xd6, 0xa6, 0xf3, 0x78, 0x26, 0x1b, 0x0b, 0x1e, 0x79, 0x50, 0x9d, 0x8b, 0xeb, 0x36, 0xaa, 0x26, 0x3d, 0xc9, 0x15, 0x45, + 0xe5, 0x33, 0x69, 0xdf, 0x26, 0x83, 0x7f, 0x39, 0x4c, 0x56, 0x77, 0x7c, 0x95, 0xb6, 0x48, 0xbd, 0x1a, 0x72, 0x92, 0x1a, 0xbf, 0x49, 0x56, 0x3f, 0x99, 0xcb, 0x9d, 0x98, 0xea, 0xb5, 0xc6, 0x66, + 0x66, 0xf6, 0xb1, 0x6f, 0x74, 0x02, 0x24, 0x81, 0xfa, 0x21, 0x4e, 0x61, 0x76, 0x98, 0xd3, 0xbb, 0xd1, 0x3c, 0xb3, 0x08, 0x71, 0x3f, 0xdc, 0xc7, 0xcf, 0xd3, 0x97, 0xb9, 0xca, 0x39, 0xaf, 0xf4, + 0xc7, 0x44, 0xd5, 0x71, 0x5d, 0x58, 0x96, 0x6f, 0x2c, 0xf9, 0x70, 0x70, 0x15, 0xc8, 0xf3, 0x54, 0x3e, 0xd2, 0x86, 0xa3, 0xd8, 0xd5, 0xcb, 0xf6, 0x4a, 0xce, 0xdf, 0xc0, 0x29, 0x71, 0xa9, 0x10, + 0x72, 0xc6, 0x9d, 0x2e, 0xf4, 0x98, 0x29, 0xf1, 0x03, 0x7f, 0x05, 0x0c, 0x5b, 0x92, 0x22, 0x98, 0x56, 0xcb, 0x12, 0xb4, 0x56, 0xcc, 0x09, 0x52, 0x82, 0xa6, 0x26, 0x87, 0xea, 0x38, 0xc9, 0x77, + 0x8a, 0xea, 0x49, 0x1d, 0xff, 0x06, 0x97, 0x11, 0xfb, 0xbe, 0x05, 0xe8, 0xcd, 0x9b, 0xf4, 0x4a, 0x8e, 0x71, 0x26, 0x19, 0x57, 0x3e, 0x12, 0xea, 0xa7, 0xb2, 0x38, 0x29, 0xdc, 0x67, 0x26, 0xbf, + 0xe3, 0x3d, 0xa1, 0x36, 0xb8, 0x1e, 0x15, 0x32, 0x51, 0x50, 0x8f, 0x62, 0x85, 0xba, 0x15, 0xb2, 0xc1, 0x23, 0x76, 0x77, 0xfe, 0x5b, 0x14, 0xb4, 0xe3, 0x3f, 0x98, 0xc3, 0x26, 0xbc, 0x58, 0xb9, + 0xd8, 0xe0, 0x75, 0xa2, 0x5b, 0x94, 0xc8, 0xa2, 0x32, 0x33, 0x02, 0x9d, 0xcc, 0x78, 0x6b, 0x13, 0x5c, 0x56, 0x16, 0x4b, 0xa3, 0xd1, 0x60, 0xcb, 0xce, 0xa8, 0x54, 0xb7, 0x97, 0x1f, 0x9c, 0xd7, + 0x3a, 0x38, 0x3a, 0xac, 0x05, 0x0a, 0x30, 0x2a, 0xd8, 0x3b, 0x3e, 0x3a, 0xb9, 0x02, 0x46, 0xad, 0x16, 0x0a, 0x32, 0x1d, 0x33, 0x0a, 0xcd, 0xec, 0x7c, 0xa6, 0x64, 0x3d, 0x7e, 0xc0, 0x1f, 0x91, + 0x69, 0x1f, 0x16, 0x32, 0x5b, 0xdf, 0x39, 0x69, 0x50, 0xb8, 0x8d, 0xaf, 0xe3, 0x69, 0xc6, 0x54, 0xb8, 0x52, 0x05, 0x5c, 0x97, 0x03, 0x62, 0xc6, 0x13, 0x80, 0x46, 0x07, 0x57, 0xc6, 0x58, 0x90, + 0xf4, 0xe5, 0x92, 0x22, 0xe4, 0xa4, 0x06, 0x0b, 0x26, 0xc0, 0xeb, 0xc1, 0x01, 0x97, 0x59, 0x0d, 0xe3, 0xc8, 0xf0, 0x95, 0x5d, 0x65, 0x4b, 0x37, 0x1c, 0xcb, 0x90, 0xac, 0xa3, 0x71, 0xb2, 0x94, + 0x47, 0x6c, 0x16, 0xa4, 0x59, 0x6a, 0x1d, 0xe8, 0x30, 0x9e, 0x2a, 0x36, 0x12, 0xc6, 0x9b, 0x71, 0x25, 0x31, 0x05, 0x01, 0xe0, 0xc0, 0x49, 0xb8, 0x74, 0x40, 0xd9, 0xa6, 0xd0, 0xec, 0xb9, 0x99, + 0xc9, 0xa0, 0x94, 0x2a, 0xa3, 0x40, 0xf6, 0x03, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, + 0x54, 0xa3, 0x16, 0x65, 0x29, 0xb5, 0x39, 0x22, 0xde, 0xe4, 0xab, 0xa0, 0x00, 0x38, 0x95, 0x81, 0x71, 0x7d, 0x36, 0xf5, 0x6f, 0x39, 0xaf, 0x73, 0x00, 0xb3, 0x1d, 0x83, 0x1a, 0x4d, 0x8c, 0x97, + 0x61, 0x28, 0xe0, 0x9d, 0xed, 0xe7, 0x1a, 0x5a, 0x86, 0x26, 0xed, 0x79, 0xd4, 0x51, 0x14, 0x08, 0x00, 0xe0, 0x3b, 0x59, 0xb9, 0x56, 0xf8, 0x21, 0x0e, 0x55, 0x60, 0x67, 0x40, 0x7d, 0x13, 0xdc, + 0x90, 0xfa, 0x9e, 0x8b, 0x87, 0x2b, 0xfb, 0x8f, 0xa0, 0x82, 0x04, 0xe5, 0x03, 0x82, 0x04, 0xe1, 0x00, 0xa0, 0xb7, 0x1f, 0x67, 0xc6, 0xce, 0xc0, 0xd3, 0x56, 0x86, 0xd5, 0x13, 0x42, 0x34, 0x32, + 0xe5, 0x12, 0xac, 0x40, 0x44, 0x55, 0x7e, 0x86, 0x8a, 0x62, 0x48, 0x00, 0x10, 0x9a, 0x33, 0x55, 0xf9, 0x8f, 0x15, 0x14, 0x44, 0xe2, 0x85, 0x2e, 0x27, 0xea, 0x6e, 0xdb, 0x19, 0x92, 0xca, 0xd3, + 0x97, 0x3c, 0x3a, 0x6f, 0xf7, 0x9a, 0x5a, 0x04, 0x9a, 0x25, 0x9e, 0xb5, 0x41, 0x5a, 0xa2, 0xa2, 0x62, 0x45, 0x6e, 0xc9, 0x49, 0x5b, 0xbb, 0x52, 0x00, 0xd8, 0xd3, 0x16, 0x3a, 0x5b, 0x10, 0x22, + 0x62, 0x92, 0xec, 0xa0, 0x10, 0x21, 0x38, 0x9d, 0xa3, 0x78, 0x81, 0xe2, 0x76, 0x30, 0x65, 0x50, 0xc6, 0xef, 0xb6, 0x44, 0x0e, 0xc5, 0x1a, 0x2f, 0x73, 0x48, 0x34, 0x9b, 0x85, 0x1c, 0xd4, 0xaa, + 0x01, 0x75, 0xa0, 0x55, 0x02, 0x13, 0xc4, 0x79, 0x1d, 0x91, 0x01, 0x12, 0x20, 0x82, 0x4b, 0x2b, 0x61, 0x65, 0x08, 0x13, 0xad, 0xfd, 0x2c, 0xb1, 0x05, 0x38, 0xbf, 0xab, 0x0a, 0x72, 0x6f, 0x81, + 0x12, 0x9e, 0xd2, 0xc0, 0xf0, 0x6a, 0x16, 0xb7, 0x01, 0x09, 0x0b, 0xf0, 0x48, 0xc5, 0xa4, 0x01, 0x26, 0xd5, 0x72, 0xfc, 0xd4, 0x7a, 0xa1, 0x21, 0x8f, 0xb0, 0x15, 0x47, 0xd1, 0x50, 0x79, 0x2d, + 0x23, 0x16, 0xcb, 0x32, 0x0d, 0x51, 0x44, 0xba, 0x35, 0x08, 0xa1, 0xeb, 0xbb, 0x5a, 0xc1, 0xc2, 0x29, 0x13, 0xe8, 0x29, 0x5f, 0xab, 0x59, 0xbf, 0x58, 0x37, 0xa7, 0x78, 0xcf, 0x28, 0x22, 0x7e, + 0x07, 0xe1, 0x03, 0x2d, 0xab, 0x7d, 0x0e, 0x09, 0xa1, 0x5f, 0x13, 0x41, 0x48, 0xc1, 0x20, 0x09, 0xda, 0x53, 0x6b, 0x22, 0xcc, 0x62, 0x47, 0x4e, 0x69, 0xcc, 0x15, 0x54, 0xc0, 0x81, 0x4d, 0x6c, + 0xa0, 0xb7, 0x22, 0x59, 0x43, 0x83, 0xa9, 0xd0, 0xa2, 0xc7, 0x7f, 0xd3, 0x65, 0xa5, 0x54, 0x42, 0x95, 0xfb, 0xb9, 0x73, 0xf9, 0x1e, 0xa5, 0x64, 0x90, 0xd6, 0xca, 0x68, 0x76, 0x49, 0x7b, 0x98, + 0xb3, 0xcb, 0x12, 0x41, 0x7c, 0x25, 0x7b, 0x6d, 0x0f, 0x71, 0x83, 0xdb, 0xb6, 0x9e, 0x33, 0x07, 0x5b, 0xeb, 0x01, 0x17, 0xb6, 0x91, 0x4c, 0x69, 0xba, 0x38, 0x34, 0x94, 0x22, 0xf2, 0xf4, 0x33, + 0x64, 0x82, 0x2a, 0x25, 0x70, 0x95, 0x2d, 0xd5, 0x07, 0x7b, 0x90, 0x75, 0x5f, 0x15, 0x74, 0x11, 0x5b, 0x8e, 0x22, 0x14, 0x27, 0x58, 0x59, 0x61, 0x91, 0x3a, 0x9b, 0xfa, 0x05, 0x02, 0xb5, 0xd7, + 0x9a, 0xb7, 0x81, 0x17, 0x44, 0xe6, 0x56, 0x3c, 0x5b, 0x62, 0xc5, 0xcc, 0x4e, 0x93, 0x23, 0x9a, 0x0a, 0x8c, 0xc6, 0x0f, 0xe8, 0x48, 0xf8, 0x4a, 0x95, 0xf5, 0x90, 0x25, 0x99, 0xb5, 0x4a, 0x06, + 0x62, 0x93, 0xa2, 0x02, 0x1d, 0xa1, 0x96, 0x76, 0x6c, 0x17, 0xc7, 0xe8, 0x63, 0xaf, 0x79, 0x0c, 0x27, 0x0b, 0x21, 0x6a, 0x25, 0x13, 0x8d, 0xda, 0x0c, 0x81, 0x26, 0xe0, 0x93, 0x77, 0x87, 0x98, + 0x59, 0xdb, 0x35, 0x8f, 0x9b, 0x82, 0xb7, 0xc8, 0xa6, 0x79, 0x2a, 0xce, 0xe9, 0x2a, 0x4c, 0xbd, 0xe3, 0xce, 0xdd, 0x45, 0x00, 0xac, 0xbc, 0x55, 0x5c, 0x28, 0x8e, 0xff, 0x97, 0x95, 0x26, 0x5b, + 0x90, 0x05, 0x35, 0x1c, 0x52, 0xe2, 0x65, 0x35, 0x54, 0xab, 0xaa, 0xf8, 0x72, 0xdf, 0x95, 0xca, 0x7f, 0x79, 0x59, 0x03, 0xf0, 0xb0, 0xa1, 0x82, 0xb1, 0x8a, 0xeb, 0x04, 0x75, 0xb2, 0x9f, 0x6e, + 0x3a, 0xbf, 0x4c, 0x22, 0x50, 0xfe, 0x7b, 0x84, 0x2a, 0x73, 0x65, 0x50, 0x16, 0xa8, 0xfc, 0x72, 0x9f, 0x39, 0x05, 0x07, 0xac, 0xa9, 0x36, 0x82, 0x5a, 0x98, 0xb3, 0xa3, 0x2e, 0x6b, 0x25, 0x54, + 0xce, 0x95, 0x28, 0x94, 0x1a, 0x3b, 0xb8, 0xc9, 0x09, 0x96, 0x00, 0x8d, 0x74, 0xfb, 0xcd, 0x02, 0x0a, 0x02, 0xe7, 0x06, 0xa6, 0xde, 0x7b, 0x02, 0xaf, 0x40, 0x4c, 0x10, 0xdb, 0x00, 0xfa, 0xec, + 0x02, 0xd3, 0xea, 0xa6, 0xd9, 0x56, 0x1a, 0x15, 0x65, 0xa7, 0xb0, 0x5c, 0x63, 0x66, 0xd0, 0x9d, 0xa7, 0xa5, 0x37, 0xf2, 0x0c, 0x7b, 0x28, 0x59, 0xa8, 0x3e, 0x02, 0x9e, 0x13, 0xa9, 0xbd, 0x28, + 0x91, 0x57, 0xc5, 0xb7, 0x4c, 0x84, 0xea, 0xa3, 0x07, 0x75, 0x3d, 0x43, 0x12, 0x02, 0xa3, 0xd9, 0xb6, 0x16, 0x22, 0x18, 0xbe, 0xc5, 0x34, 0x69, 0x45, 0xbf, 0xef, 0x55, 0xb6, 0x24, 0xc5, 0xc6, + 0xe3, 0x73, 0x35, 0x9b, 0xb1, 0xc4, 0x79, 0x95, 0x2b, 0xba, 0xba, 0x4d, 0x65, 0x55, 0xc2, 0x76, 0x57, 0x3e, 0x51, 0x52, 0xb5, 0x53, 0x90, 0x19, 0x99, 0xf6, 0x94, 0x02, 0xd1, 0x50, 0xbe, 0xf7, + 0x9d, 0x74, 0xfb, 0x29, 0x53, 0x01, 0x8f, 0xf4, 0x86, 0x66, 0x74, 0x6a, 0xce, 0x60, 0x78, 0x14, 0xa1, 0xfa, 0x33, 0x19, 0x57, 0x20, 0xf8, 0x38, 0x78, 0xd3, 0xb5, 0x75, 0xc7, 0x25, 0x74, 0x4a, + 0x72, 0x07, 0x0d, 0xd0, 0x44, 0x01, 0x80, 0x42, 0xda, 0x25, 0x71, 0x4d, 0x17, 0x30, 0x90, 0x32, 0x3a, 0x51, 0xe6, 0xc0, 0x63, 0xd2, 0x03, 0x88, 0x13, 0x80, 0x91, 0x27, 0x61, 0xfc, 0x34, 0x10, + 0x83, 0x90, 0x95, 0xf2, 0x6c, 0x0e, 0x68, 0x7a, 0x00, 0x70, 0x54, 0x95, 0xe1, 0x71, 0xb5, 0x71, 0x51, 0xac, 0xe0, 0x49, 0x8e, 0x30, 0xf1, 0x4c, 0xa9, 0xb0, 0x2f, 0x6e, 0x40, 0x83, 0x18, 0x54, + 0xc2, 0xe0, 0xab, 0x1e, 0xcd, 0x0c, 0x21, 0xd8, 0xe4, 0xc7, 0xe6, 0x69, 0xcd, 0x72, 0x82, 0x30, 0xb9, 0xd1, 0x1f, 0x72, 0xc2, 0x66, 0xe3, 0x44, 0x66, 0xf9, 0xc0, 0x15, 0x9e, 0xf4, 0x24, 0xf8, + 0xf3, 0x1d, 0x95, 0xa5, 0x7b, 0xa0, 0xe2, 0x10, 0x54, 0x3c, 0x10, 0xc6, 0x50, 0x3f, 0xb5, 0xc6, 0x3e, 0xd2, 0x3a, 0xa3, 0x6c, 0xd6, 0xa6, 0xf3, 0x78, 0x26, 0x1b, 0x0b, 0x1e, 0x79, 0x50, 0x9d, + 0x8b, 0xeb, 0x36, 0xaa, 0x26, 0x3d, 0xc9, 0x15, 0x45, 0xe5, 0x33, 0x69, 0xdf, 0x26, 0x83, 0x7f, 0x39, 0x4c, 0x56, 0x77, 0x7c, 0x95, 0xb6, 0x48, 0xbd, 0x1a, 0x72, 0x92, 0x1a, 0xbf, 0x49, 0x56, + 0x3f, 0x99, 0xcb, 0x9d, 0x98, 0xea, 0xb5, 0xc6, 0x66, 0x66, 0xf6, 0xb1, 0x6f, 0x74, 0x02, 0x24, 0x81, 0xfa, 0x21, 0x4e, 0x61, 0x76, 0x98, 0xd3, 0xbb, 0xd1, 0x3c, 0xb3, 0x08, 0x71, 0x3f, 0xdc, + 0xc7, 0xcf, 0xd3, 0x97, 0xb9, 0xca, 0x39, 0xaf, 0xf4, 0xc7, 0x44, 0xd5, 0x71, 0x5d, 0x58, 0x96, 0x6f, 0x2c, 0xf9, 0x70, 0x70, 0x15, 0xc8, 0xf3, 0x54, 0x3e, 0xd2, 0x86, 0xa3, 0xd8, 0xd5, 0xcb, + 0xf6, 0x4a, 0xce, 0xdf, 0xc0, 0x29, 0x71, 0xa9, 0x10, 0x72, 0xc6, 0x9d, 0x2e, 0xf4, 0x98, 0x29, 0xf1, 0x03, 0x7f, 0x05, 0x0c, 0x5b, 0x92, 0x22, 0x98, 0x56, 0xcb, 0x12, 0xb4, 0x56, 0xcc, 0x09, + 0x52, 0x82, 0xa6, 0x26, 0x87, 0xea, 0x38, 0xc9, 0x77, 0x8a, 0xea, 0x49, 0x1d, 0xff, 0x06, 0x97, 0x11, 0xfb, 0xbe, 0x05, 0xe8, 0xcd, 0x9b, 0xf4, 0x4a, 0x8e, 0x71, 0x26, 0x19, 0x57, 0x3e, 0x12, + 0xea, 0xa7, 0xb2, 0x38, 0x29, 0xdc, 0x67, 0x26, 0xbf, 0xe3, 0x3d, 0xa1, 0x36, 0xb8, 0x1e, 0x15, 0x32, 0x51, 0x50, 0x8f, 0x62, 0x85, 0xba, 0x15, 0xb2, 0xc1, 0x23, 0x76, 0x77, 0xfe, 0x5b, 0x14, + 0xb4, 0xe3, 0x3f, 0x98, 0xc3, 0x26, 0xbc, 0x58, 0xb9, 0xd8, 0xe0, 0x75, 0xa2, 0x5b, 0x94, 0xc8, 0xa2, 0x32, 0x33, 0x02, 0x9d, 0xcc, 0x78, 0x6b, 0x13, 0x5c, 0x56, 0x16, 0x4b, 0xa3, 0xd1, 0x60, + 0xcb, 0xce, 0xa8, 0x54, 0xb7, 0x97, 0x1f, 0x9c, 0xd7, 0x3a, 0x38, 0x3a, 0xac, 0x05, 0x0a, 0x30, 0x2a, 0xd8, 0x3b, 0x3e, 0x3a, 0xb9, 0x02, 0x46, 0xad, 0x16, 0x0a, 0x32, 0x1d, 0x33, 0x0a, 0xcd, + 0xec, 0x7c, 0xa6, 0x64, 0x3d, 0x7e, 0xc0, 0x1f, 0x91, 0x69, 0x1f, 0x16, 0x32, 0x5b, 0xdf, 0x39, 0x69, 0x50, 0xb8, 0x8d, 0xaf, 0xe3, 0x69, 0xc6, 0x54, 0xb8, 0x52, 0x05, 0x5c, 0x97, 0x03, 0x62, + 0xc6, 0x13, 0x80, 0x46, 0x07, 0x57, 0xc6, 0x58, 0x90, 0xf4, 0xe5, 0x92, 0x22, 0xe4, 0xa4, 0x06, 0x0b, 0x26, 0xc0, 0xeb, 0xc1, 0x01, 0x97, 0x59, 0x0d, 0xe3, 0xc8, 0xf0, 0x95, 0x5d, 0x65, 0x4b, + 0x37, 0x1c, 0xcb, 0x90, 0xac, 0xa3, 0x71, 0xb2, 0x94, 0x47, 0x6c, 0x16, 0xa4, 0x59, 0x6a, 0x1d, 0xe8, 0x30, 0x9e, 0x2a, 0x36, 0x12, 0xc6, 0x9b, 0x71, 0x25, 0x31, 0x05, 0x01, 0xe0, 0xc0, 0x49, + 0xb8, 0x74, 0x40, 0xd9, 0xa6, 0xd0, 0xec, 0xb9, 0x99, 0xc9, 0xa0, 0x94, 0x2a, 0xa3, 0x40, 0xf6, 0x03, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, + 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, 0x54, 0xa3, 0x16, 0x65, 0x29, 0xb5, 0x39, 0x22, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + }, + .spki_len = 1219, + .spki = { + 0x30, 0x82, 0x04, 0xbf, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x05, 0x03, 0x03, 0x05, 0x00, 0x03, 0x82, 0x04, 0xaa, 0x00, 0x30, 0x82, 0x04, 0xa5, 0x03, 0x82, + 0x04, 0xa1, 0x00, 0xa0, 0xb7, 0x1f, 0x67, 0xc6, 0xce, 0xc0, 0xd3, 0x56, 0x86, 0xd5, 0x13, 0x42, 0x34, 0x32, 0xe5, 0x12, 0xac, 0x40, 0x44, 0x55, 0x7e, 0x86, 0x8a, 0x62, 0x48, 0x00, 0x10, 0x9a, + 0x33, 0x55, 0xf9, 0x8f, 0x15, 0x14, 0x44, 0xe2, 0x85, 0x2e, 0x27, 0xea, 0x6e, 0xdb, 0x19, 0x92, 0xca, 0xd3, 0x97, 0x3c, 0x3a, 0x6f, 0xf7, 0x9a, 0x5a, 0x04, 0x9a, 0x25, 0x9e, 0xb5, 0x41, 0x5a, + 0xa2, 0xa2, 0x62, 0x45, 0x6e, 0xc9, 0x49, 0x5b, 0xbb, 0x52, 0x00, 0xd8, 0xd3, 0x16, 0x3a, 0x5b, 0x10, 0x22, 0x62, 0x92, 0xec, 0xa0, 0x10, 0x21, 0x38, 0x9d, 0xa3, 0x78, 0x81, 0xe2, 0x76, 0x30, + 0x65, 0x50, 0xc6, 0xef, 0xb6, 0x44, 0x0e, 0xc5, 0x1a, 0x2f, 0x73, 0x48, 0x34, 0x9b, 0x85, 0x1c, 0xd4, 0xaa, 0x01, 0x75, 0xa0, 0x55, 0x02, 0x13, 0xc4, 0x79, 0x1d, 0x91, 0x01, 0x12, 0x20, 0x82, + 0x4b, 0x2b, 0x61, 0x65, 0x08, 0x13, 0xad, 0xfd, 0x2c, 0xb1, 0x05, 0x38, 0xbf, 0xab, 0x0a, 0x72, 0x6f, 0x81, 0x12, 0x9e, 0xd2, 0xc0, 0xf0, 0x6a, 0x16, 0xb7, 0x01, 0x09, 0x0b, 0xf0, 0x48, 0xc5, + 0xa4, 0x01, 0x26, 0xd5, 0x72, 0xfc, 0xd4, 0x7a, 0xa1, 0x21, 0x8f, 0xb0, 0x15, 0x47, 0xd1, 0x50, 0x79, 0x2d, 0x23, 0x16, 0xcb, 0x32, 0x0d, 0x51, 0x44, 0xba, 0x35, 0x08, 0xa1, 0xeb, 0xbb, 0x5a, + 0xc1, 0xc2, 0x29, 0x13, 0xe8, 0x29, 0x5f, 0xab, 0x59, 0xbf, 0x58, 0x37, 0xa7, 0x78, 0xcf, 0x28, 0x22, 0x7e, 0x07, 0xe1, 0x03, 0x2d, 0xab, 0x7d, 0x0e, 0x09, 0xa1, 0x5f, 0x13, 0x41, 0x48, 0xc1, + 0x20, 0x09, 0xda, 0x53, 0x6b, 0x22, 0xcc, 0x62, 0x47, 0x4e, 0x69, 0xcc, 0x15, 0x54, 0xc0, 0x81, 0x4d, 0x6c, 0xa0, 0xb7, 0x22, 0x59, 0x43, 0x83, 0xa9, 0xd0, 0xa2, 0xc7, 0x7f, 0xd3, 0x65, 0xa5, + 0x54, 0x42, 0x95, 0xfb, 0xb9, 0x73, 0xf9, 0x1e, 0xa5, 0x64, 0x90, 0xd6, 0xca, 0x68, 0x76, 0x49, 0x7b, 0x98, 0xb3, 0xcb, 0x12, 0x41, 0x7c, 0x25, 0x7b, 0x6d, 0x0f, 0x71, 0x83, 0xdb, 0xb6, 0x9e, + 0x33, 0x07, 0x5b, 0xeb, 0x01, 0x17, 0xb6, 0x91, 0x4c, 0x69, 0xba, 0x38, 0x34, 0x94, 0x22, 0xf2, 0xf4, 0x33, 0x64, 0x82, 0x2a, 0x25, 0x70, 0x95, 0x2d, 0xd5, 0x07, 0x7b, 0x90, 0x75, 0x5f, 0x15, + 0x74, 0x11, 0x5b, 0x8e, 0x22, 0x14, 0x27, 0x58, 0x59, 0x61, 0x91, 0x3a, 0x9b, 0xfa, 0x05, 0x02, 0xb5, 0xd7, 0x9a, 0xb7, 0x81, 0x17, 0x44, 0xe6, 0x56, 0x3c, 0x5b, 0x62, 0xc5, 0xcc, 0x4e, 0x93, + 0x23, 0x9a, 0x0a, 0x8c, 0xc6, 0x0f, 0xe8, 0x48, 0xf8, 0x4a, 0x95, 0xf5, 0x90, 0x25, 0x99, 0xb5, 0x4a, 0x06, 0x62, 0x93, 0xa2, 0x02, 0x1d, 0xa1, 0x96, 0x76, 0x6c, 0x17, 0xc7, 0xe8, 0x63, 0xaf, + 0x79, 0x0c, 0x27, 0x0b, 0x21, 0x6a, 0x25, 0x13, 0x8d, 0xda, 0x0c, 0x81, 0x26, 0xe0, 0x93, 0x77, 0x87, 0x98, 0x59, 0xdb, 0x35, 0x8f, 0x9b, 0x82, 0xb7, 0xc8, 0xa6, 0x79, 0x2a, 0xce, 0xe9, 0x2a, + 0x4c, 0xbd, 0xe3, 0xce, 0xdd, 0x45, 0x00, 0xac, 0xbc, 0x55, 0x5c, 0x28, 0x8e, 0xff, 0x97, 0x95, 0x26, 0x5b, 0x90, 0x05, 0x35, 0x1c, 0x52, 0xe2, 0x65, 0x35, 0x54, 0xab, 0xaa, 0xf8, 0x72, 0xdf, + 0x95, 0xca, 0x7f, 0x79, 0x59, 0x03, 0xf0, 0xb0, 0xa1, 0x82, 0xb1, 0x8a, 0xeb, 0x04, 0x75, 0xb2, 0x9f, 0x6e, 0x3a, 0xbf, 0x4c, 0x22, 0x50, 0xfe, 0x7b, 0x84, 0x2a, 0x73, 0x65, 0x50, 0x16, 0xa8, + 0xfc, 0x72, 0x9f, 0x39, 0x05, 0x07, 0xac, 0xa9, 0x36, 0x82, 0x5a, 0x98, 0xb3, 0xa3, 0x2e, 0x6b, 0x25, 0x54, 0xce, 0x95, 0x28, 0x94, 0x1a, 0x3b, 0xb8, 0xc9, 0x09, 0x96, 0x00, 0x8d, 0x74, 0xfb, + 0xcd, 0x02, 0x0a, 0x02, 0xe7, 0x06, 0xa6, 0xde, 0x7b, 0x02, 0xaf, 0x40, 0x4c, 0x10, 0xdb, 0x00, 0xfa, 0xec, 0x02, 0xd3, 0xea, 0xa6, 0xd9, 0x56, 0x1a, 0x15, 0x65, 0xa7, 0xb0, 0x5c, 0x63, 0x66, + 0xd0, 0x9d, 0xa7, 0xa5, 0x37, 0xf2, 0x0c, 0x7b, 0x28, 0x59, 0xa8, 0x3e, 0x02, 0x9e, 0x13, 0xa9, 0xbd, 0x28, 0x91, 0x57, 0xc5, 0xb7, 0x4c, 0x84, 0xea, 0xa3, 0x07, 0x75, 0x3d, 0x43, 0x12, 0x02, + 0xa3, 0xd9, 0xb6, 0x16, 0x22, 0x18, 0xbe, 0xc5, 0x34, 0x69, 0x45, 0xbf, 0xef, 0x55, 0xb6, 0x24, 0xc5, 0xc6, 0xe3, 0x73, 0x35, 0x9b, 0xb1, 0xc4, 0x79, 0x95, 0x2b, 0xba, 0xba, 0x4d, 0x65, 0x55, + 0xc2, 0x76, 0x57, 0x3e, 0x51, 0x52, 0xb5, 0x53, 0x90, 0x19, 0x99, 0xf6, 0x94, 0x02, 0xd1, 0x50, 0xbe, 0xf7, 0x9d, 0x74, 0xfb, 0x29, 0x53, 0x01, 0x8f, 0xf4, 0x86, 0x66, 0x74, 0x6a, 0xce, 0x60, + 0x78, 0x14, 0xa1, 0xfa, 0x33, 0x19, 0x57, 0x20, 0xf8, 0x38, 0x78, 0xd3, 0xb5, 0x75, 0xc7, 0x25, 0x74, 0x4a, 0x72, 0x07, 0x0d, 0xd0, 0x44, 0x01, 0x80, 0x42, 0xda, 0x25, 0x71, 0x4d, 0x17, 0x30, + 0x90, 0x32, 0x3a, 0x51, 0xe6, 0xc0, 0x63, 0xd2, 0x03, 0x88, 0x13, 0x80, 0x91, 0x27, 0x61, 0xfc, 0x34, 0x10, 0x83, 0x90, 0x95, 0xf2, 0x6c, 0x0e, 0x68, 0x7a, 0x00, 0x70, 0x54, 0x95, 0xe1, 0x71, + 0xb5, 0x71, 0x51, 0xac, 0xe0, 0x49, 0x8e, 0x30, 0xf1, 0x4c, 0xa9, 0xb0, 0x2f, 0x6e, 0x40, 0x83, 0x18, 0x54, 0xc2, 0xe0, 0xab, 0x1e, 0xcd, 0x0c, 0x21, 0xd8, 0xe4, 0xc7, 0xe6, 0x69, 0xcd, 0x72, + 0x82, 0x30, 0xb9, 0xd1, 0x1f, 0x72, 0xc2, 0x66, 0xe3, 0x44, 0x66, 0xf9, 0xc0, 0x15, 0x9e, 0xf4, 0x24, 0xf8, 0xf3, 0x1d, 0x95, 0xa5, 0x7b, 0xa0, 0xe2, 0x10, 0x54, 0x3c, 0x10, 0xc6, 0x50, 0x3f, + 0xb5, 0xc6, 0x3e, 0xd2, 0x3a, 0xa3, 0x6c, 0xd6, 0xa6, 0xf3, 0x78, 0x26, 0x1b, 0x0b, 0x1e, 0x79, 0x50, 0x9d, 0x8b, 0xeb, 0x36, 0xaa, 0x26, 0x3d, 0xc9, 0x15, 0x45, 0xe5, 0x33, 0x69, 0xdf, 0x26, + 0x83, 0x7f, 0x39, 0x4c, 0x56, 0x77, 0x7c, 0x95, 0xb6, 0x48, 0xbd, 0x1a, 0x72, 0x92, 0x1a, 0xbf, 0x49, 0x56, 0x3f, 0x99, 0xcb, 0x9d, 0x98, 0xea, 0xb5, 0xc6, 0x66, 0x66, 0xf6, 0xb1, 0x6f, 0x74, + 0x02, 0x24, 0x81, 0xfa, 0x21, 0x4e, 0x61, 0x76, 0x98, 0xd3, 0xbb, 0xd1, 0x3c, 0xb3, 0x08, 0x71, 0x3f, 0xdc, 0xc7, 0xcf, 0xd3, 0x97, 0xb9, 0xca, 0x39, 0xaf, 0xf4, 0xc7, 0x44, 0xd5, 0x71, 0x5d, + 0x58, 0x96, 0x6f, 0x2c, 0xf9, 0x70, 0x70, 0x15, 0xc8, 0xf3, 0x54, 0x3e, 0xd2, 0x86, 0xa3, 0xd8, 0xd5, 0xcb, 0xf6, 0x4a, 0xce, 0xdf, 0xc0, 0x29, 0x71, 0xa9, 0x10, 0x72, 0xc6, 0x9d, 0x2e, 0xf4, + 0x98, 0x29, 0xf1, 0x03, 0x7f, 0x05, 0x0c, 0x5b, 0x92, 0x22, 0x98, 0x56, 0xcb, 0x12, 0xb4, 0x56, 0xcc, 0x09, 0x52, 0x82, 0xa6, 0x26, 0x87, 0xea, 0x38, 0xc9, 0x77, 0x8a, 0xea, 0x49, 0x1d, 0xff, + 0x06, 0x97, 0x11, 0xfb, 0xbe, 0x05, 0xe8, 0xcd, 0x9b, 0xf4, 0x4a, 0x8e, 0x71, 0x26, 0x19, 0x57, 0x3e, 0x12, 0xea, 0xa7, 0xb2, 0x38, 0x29, 0xdc, 0x67, 0x26, 0xbf, 0xe3, 0x3d, 0xa1, 0x36, 0xb8, + 0x1e, 0x15, 0x32, 0x51, 0x50, 0x8f, 0x62, 0x85, 0xba, 0x15, 0xb2, 0xc1, 0x23, 0x76, 0x77, 0xfe, 0x5b, 0x14, 0xb4, 0xe3, 0x3f, 0x98, 0xc3, 0x26, 0xbc, 0x58, 0xb9, 0xd8, 0xe0, 0x75, 0xa2, 0x5b, + 0x94, 0xc8, 0xa2, 0x32, 0x33, 0x02, 0x9d, 0xcc, 0x78, 0x6b, 0x13, 0x5c, 0x56, 0x16, 0x4b, 0xa3, 0xd1, 0x60, 0xcb, 0xce, 0xa8, 0x54, 0xb7, 0x97, 0x1f, 0x9c, 0xd7, 0x3a, 0x38, 0x3a, 0xac, 0x05, + 0x0a, 0x30, 0x2a, 0xd8, 0x3b, 0x3e, 0x3a, 0xb9, 0x02, 0x46, 0xad, 0x16, 0x0a, 0x32, 0x1d, 0x33, 0x0a, 0xcd, 0xec, 0x7c, 0xa6, 0x64, 0x3d, 0x7e, 0xc0, 0x1f, 0x91, 0x69, 0x1f, 0x16, 0x32, 0x5b, + 0xdf, 0x39, 0x69, 0x50, 0xb8, 0x8d, 0xaf, 0xe3, 0x69, 0xc6, 0x54, 0xb8, 0x52, 0x05, 0x5c, 0x97, 0x03, 0x62, 0xc6, 0x13, 0x80, 0x46, 0x07, 0x57, 0xc6, 0x58, 0x90, 0xf4, 0xe5, 0x92, 0x22, 0xe4, + 0xa4, 0x06, 0x0b, 0x26, 0xc0, 0xeb, 0xc1, 0x01, 0x97, 0x59, 0x0d, 0xe3, 0xc8, 0xf0, 0x95, 0x5d, 0x65, 0x4b, 0x37, 0x1c, 0xcb, 0x90, 0xac, 0xa3, 0x71, 0xb2, 0x94, 0x47, 0x6c, 0x16, 0xa4, 0x59, + 0x6a, 0x1d, 0xe8, 0x30, 0x9e, 0x2a, 0x36, 0x12, 0xc6, 0x9b, 0x71, 0x25, 0x31, 0x05, 0x01, 0xe0, 0xc0, 0x49, 0xb8, 0x74, 0x40, 0xd9, 0xa6, 0xd0, 0xec, 0xb9, 0x99, 0xc9, 0xa0, 0x94, 0x2a, 0xa3, + 0x40, 0xf6, 0x03, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, 0x54, 0xa3, 0x16, 0x65, 0x29, + 0xb5, 0x39, 0x22, + }, + .secret_len = 32, + .secret = { + 0xed, 0x20, 0x14, 0x0c, 0x05, 0xd7, 0x8b, 0x15, 0xf2, 0xe4, 0x12, 0x67, 0x1a, 0x84, 0x15, 0x42, 0x17, 0xfd, 0x77, 0x61, 0x9a, 0x2c, 0x52, 0x2d, 0x3c, 0x3c, 0xb6, 0x88, 0xcb, 0x34, 0xc6, 0x8b, + }, + .cipher_len = 1088, + .cipher = { + 0xea, 0xdd, 0x5a, 0xda, 0x14, 0xda, 0x57, 0xf0, 0xae, 0xf3, 0x50, 0x5f, 0x1c, 0xaa, 0x64, 0x85, 0xd4, 0x23, 0x8d, 0x99, 0x9a, 0x3e, 0xf4, 0xb0, 0xa5, 0x9a, 0x1c, 0xdb, 0xe0, 0xa2, 0x7e, 0x47, + 0x85, 0x47, 0xa3, 0xa9, 0x9d, 0x2a, 0xb0, 0x9a, 0xc7, 0xd7, 0xc8, 0xf5, 0xae, 0x3d, 0x64, 0x32, 0x04, 0x5c, 0xba, 0x3f, 0xa7, 0x78, 0x34, 0x58, 0x92, 0x54, 0x2b, 0xd8, 0x1c, 0x05, 0xbe, 0xfc, + 0xd2, 0xe5, 0xcc, 0x9a, 0x57, 0x9b, 0xef, 0xb7, 0xc5, 0x8d, 0x02, 0xfb, 0x94, 0xf3, 0x33, 0x92, 0xfe, 0x17, 0xf4, 0xeb, 0xa2, 0xcb, 0x51, 0x0e, 0xc7, 0x4c, 0xc9, 0xd1, 0xd8, 0xa8, 0x7c, 0x10, + 0x66, 0xa4, 0x86, 0x9a, 0x39, 0x83, 0xe6, 0x64, 0xbf, 0xe9, 0xde, 0xa5, 0xae, 0x4f, 0xdf, 0x31, 0x0c, 0x8f, 0x59, 0x81, 0x5a, 0x67, 0x8f, 0xa3, 0x25, 0xf3, 0x69, 0xaf, 0x84, 0xff, 0xeb, 0xc1, + 0xd1, 0x50, 0x43, 0x1f, 0xe3, 0xbd, 0x27, 0x34, 0xf6, 0x36, 0xcf, 0x65, 0x8e, 0x6c, 0x1a, 0x6a, 0x6e, 0x2c, 0xbe, 0x07, 0x1f, 0x9a, 0x7c, 0x26, 0x11, 0x9a, 0xd1, 0x05, 0x09, 0x8e, 0xda, 0x62, + 0x2c, 0xab, 0x8e, 0x17, 0x67, 0x62, 0x10, 0x98, 0x77, 0xd9, 0xae, 0x9d, 0x67, 0x29, 0xd4, 0x4a, 0x58, 0xe7, 0x07, 0xd6, 0xb8, 0xad, 0x6e, 0x69, 0x6a, 0x33, 0xc6, 0x72, 0xda, 0x9d, 0x08, 0xda, + 0x2a, 0x7f, 0x9e, 0x3b, 0xf0, 0x22, 0x18, 0x23, 0x87, 0x22, 0xa4, 0x6b, 0x31, 0xd4, 0x9d, 0xaf, 0xf9, 0xaf, 0x00, 0xa6, 0x36, 0x3c, 0x3a, 0x42, 0x3b, 0x2e, 0x87, 0x3d, 0xef, 0xdd, 0xbc, 0xd9, + 0x69, 0xb7, 0x5a, 0x81, 0x05, 0x3d, 0x9a, 0x97, 0xc0, 0x6d, 0xe2, 0xbf, 0xe3, 0xd0, 0xcf, 0xd3, 0xd3, 0xc7, 0x79, 0x83, 0xb1, 0x8d, 0xbd, 0xe2, 0x3c, 0x07, 0x28, 0x60, 0x4a, 0x71, 0x43, 0x5a, + 0xd4, 0x0d, 0xf1, 0x57, 0x90, 0x96, 0xdd, 0xbe, 0x02, 0xe4, 0x61, 0x22, 0x10, 0xca, 0xa0, 0x34, 0xdc, 0xef, 0xb8, 0xb4, 0xd7, 0xb5, 0xe6, 0xd2, 0xeb, 0xa3, 0x7a, 0x79, 0xfb, 0x61, 0xf3, 0x4b, + 0x5a, 0xf7, 0xd9, 0xb2, 0x7b, 0x13, 0xe4, 0x93, 0x62, 0x22, 0x41, 0x12, 0x49, 0xb7, 0xfb, 0xb6, 0x9e, 0x73, 0x46, 0x1d, 0xaf, 0x4a, 0xa6, 0xf3, 0xe2, 0xc7, 0x39, 0x44, 0xf1, 0x0c, 0xe6, 0x7c, + 0x86, 0xfe, 0xd2, 0x60, 0xbd, 0xa7, 0xb4, 0x0d, 0xb3, 0x9b, 0x1d, 0xe3, 0xc7, 0xd8, 0xf0, 0x9a, 0x77, 0xf3, 0xc8, 0x4b, 0xc6, 0x29, 0x31, 0xd2, 0x28, 0xb2, 0x4a, 0x57, 0x4a, 0xc3, 0xf4, 0xeb, + 0x74, 0x5c, 0xff, 0x7e, 0x03, 0x1a, 0x3f, 0xb2, 0xa0, 0x85, 0x95, 0xc1, 0x53, 0x70, 0xa3, 0xc8, 0x2d, 0xb7, 0xd9, 0xf4, 0x1b, 0xb1, 0xd8, 0xec, 0xc4, 0x29, 0xcf, 0xa3, 0xa6, 0x58, 0x33, 0x01, + 0x6a, 0xb6, 0xea, 0x60, 0xc9, 0x39, 0x0c, 0xfa, 0x1b, 0x65, 0xcc, 0xea, 0xe5, 0x50, 0x94, 0x07, 0x95, 0x38, 0x6e, 0xd2, 0x41, 0x33, 0xfb, 0xae, 0x8b, 0x30, 0x17, 0x50, 0x2a, 0xf3, 0xcf, 0xe9, + 0x51, 0xd7, 0x81, 0xd3, 0x6c, 0xfe, 0xff, 0x85, 0xbf, 0xdf, 0x5a, 0xf0, 0x40, 0xbe, 0x40, 0x65, 0x68, 0x1b, 0x3b, 0x0a, 0x63, 0xc2, 0x74, 0x7f, 0x08, 0x08, 0xcf, 0x3d, 0xa7, 0x25, 0x16, 0x9d, + 0xde, 0xd1, 0x00, 0x3d, 0xa6, 0xcd, 0x5d, 0xe4, 0xcb, 0x04, 0x19, 0x42, 0x93, 0x8d, 0x0a, 0x7f, 0x88, 0x02, 0xd4, 0x8f, 0x2e, 0x3c, 0x6e, 0xeb, 0x45, 0xcd, 0x90, 0xaf, 0x6f, 0xc9, 0xf4, 0x50, + 0x7e, 0x9f, 0x83, 0x80, 0xac, 0x33, 0xca, 0xca, 0x77, 0x51, 0x48, 0x7f, 0x65, 0x50, 0x04, 0x41, 0xd9, 0x20, 0xb9, 0x48, 0x80, 0xa4, 0x97, 0xd0, 0x1c, 0x08, 0x02, 0xbb, 0x08, 0xd7, 0x4c, 0x5d, + 0x4c, 0x6b, 0xf2, 0xd8, 0x65, 0xee, 0x58, 0x22, 0xb3, 0x37, 0x5c, 0x75, 0x5d, 0x1a, 0x5e, 0x3d, 0x32, 0x44, 0xc3, 0x20, 0x51, 0x0a, 0x1e, 0x30, 0x35, 0x77, 0x02, 0xcd, 0x42, 0x52, 0x07, 0x2c, + 0xf8, 0x64, 0x37, 0xf7, 0xa9, 0xde, 0x55, 0x61, 0xc7, 0xe5, 0x9b, 0x94, 0xb9, 0x58, 0x41, 0x00, 0x13, 0x1a, 0xc3, 0x99, 0xf4, 0xc1, 0xeb, 0x19, 0xfb, 0x4b, 0xdf, 0x65, 0xe6, 0x27, 0x85, 0xe9, + 0x7c, 0x19, 0x4b, 0x87, 0x64, 0xcc, 0xf3, 0x2f, 0xd0, 0x5d, 0x80, 0x4c, 0x2e, 0x43, 0x9d, 0xda, 0x2a, 0x10, 0x92, 0x74, 0xfb, 0xff, 0xa8, 0x1a, 0x83, 0x7c, 0x51, 0xb2, 0x6d, 0x15, 0x4f, 0x97, + 0x4b, 0x88, 0x2a, 0x5b, 0x17, 0x4b, 0x30, 0x8f, 0xc4, 0x87, 0x68, 0xd2, 0x22, 0x92, 0x25, 0x32, 0xb1, 0x83, 0xab, 0xdf, 0x6f, 0xbb, 0x0b, 0xc7, 0x49, 0x27, 0x66, 0x97, 0x4d, 0x32, 0x1e, 0xe6, + 0xfb, 0x7c, 0x5f, 0x7b, 0x3e, 0xea, 0x23, 0x78, 0xdc, 0x6d, 0x6b, 0xb4, 0x80, 0x19, 0x25, 0x0b, 0x8d, 0x8d, 0x8d, 0xed, 0xb5, 0x22, 0x42, 0x1a, 0xee, 0xdb, 0x31, 0x86, 0x76, 0x98, 0x2a, 0x80, + 0xe7, 0x96, 0x1e, 0xc4, 0x0e, 0x6d, 0x7f, 0x33, 0x39, 0x69, 0x42, 0x55, 0xba, 0xff, 0x51, 0xbe, 0x3a, 0x7e, 0xa7, 0xd8, 0x79, 0x3a, 0x10, 0x9b, 0xe3, 0xae, 0x44, 0x23, 0xbf, 0x08, 0x2e, 0x20, + 0x6a, 0x57, 0x3b, 0x4f, 0x0f, 0x93, 0xfc, 0x16, 0xdd, 0xe8, 0x1b, 0xd5, 0xdc, 0x58, 0x3f, 0x52, 0x8c, 0x08, 0xa0, 0xa9, 0xab, 0x8e, 0x6c, 0xd5, 0x24, 0xe2, 0x97, 0xc9, 0xcf, 0x0f, 0x43, 0xc3, + 0x44, 0x91, 0x38, 0x30, 0xec, 0xb1, 0x6f, 0x91, 0x44, 0x14, 0x77, 0xba, 0x78, 0x2e, 0xdd, 0x4e, 0x73, 0xe7, 0x32, 0x97, 0x9d, 0x3a, 0x66, 0x4e, 0xb9, 0x9e, 0xa5, 0xd2, 0x4b, 0x6c, 0x84, 0xaa, + 0x69, 0xf3, 0x77, 0xcb, 0x0c, 0xad, 0x5a, 0xe4, 0xe6, 0x41, 0xe3, 0x8b, 0x19, 0x7a, 0x09, 0x94, 0xd5, 0x8b, 0x23, 0x87, 0xe9, 0x17, 0x60, 0xe9, 0xb6, 0xfe, 0xbc, 0xb4, 0x45, 0xcf, 0x85, 0xbb, + 0xa2, 0x4a, 0x94, 0xcd, 0xa7, 0x5e, 0x33, 0x86, 0x74, 0x42, 0x82, 0x49, 0xfe, 0x6d, 0xe4, 0x69, 0x26, 0x01, 0xd1, 0xea, 0xe0, 0xea, 0x02, 0x1d, 0x9b, 0xc8, 0x07, 0x7b, 0xe8, 0x66, 0x5d, 0x07, + 0x37, 0x74, 0x8f, 0xa3, 0x0f, 0xcf, 0x80, 0xf7, 0xe4, 0x82, 0x58, 0x46, 0x74, 0xf6, 0x33, 0xa5, 0x00, 0x6a, 0x53, 0x82, 0x67, 0x62, 0x7f, 0xd9, 0x18, 0x54, 0xe0, 0x87, 0x12, 0x68, 0xa6, 0xb0, + 0xb0, 0x5d, 0xd5, 0x14, 0x95, 0x13, 0x5d, 0xef, 0xb9, 0x37, 0x6e, 0x9b, 0x84, 0x1b, 0x64, 0xe5, 0xdb, 0xf4, 0x3c, 0xe6, 0xc7, 0x4b, 0xcf, 0x3a, 0xe1, 0xfc, 0x42, 0x7e, 0x81, 0x0b, 0x7c, 0xbf, + 0x69, 0x57, 0xdb, 0xf9, 0x04, 0x69, 0x0e, 0x87, 0x84, 0x25, 0x43, 0x89, 0x7d, 0xe7, 0x8f, 0x13, 0xd0, 0x8d, 0x92, 0xeb, 0xd2, 0x7f, 0xb2, 0xcf, 0xcc, 0x0c, 0x76, 0x54, 0x30, 0x58, 0x90, 0x57, + 0xb1, 0x6b, 0x15, 0xf2, 0x07, 0xca, 0x1e, 0x6f, 0x08, 0xd5, 0x26, 0x16, 0xdd, 0x57, 0xad, 0x43, 0xef, 0xea, 0x6f, 0xdd, 0xaa, 0xea, 0x18, 0xd3, 0x37, 0x31, 0xfa, 0xc7, 0xec, 0xaa, 0xe9, 0x50, + 0xe1, 0xdf, 0x3c, 0x5a, 0x4e, 0x6f, 0xcb, 0x22, 0x3d, 0xf5, 0xe8, 0x6b, 0x48, 0x7f, 0xd7, 0x09, 0x2d, 0x08, 0x22, 0xef, 0xfa, 0xec, 0x82, 0xc4, 0xbe, 0xc1, 0x0c, 0x60, 0x0f, 0xdb, 0x90, 0xe7, + 0x74, 0x82, 0x91, 0x1b, 0x15, 0x95, 0x27, 0x77, 0x38, 0x84, 0x14, 0x09, 0xd0, 0xf8, 0xf1, 0x13, 0x19, 0x1d, 0x47, 0xf5, 0xe5, 0x6c, 0x11, 0x5a, 0x05, 0xde, 0xa7, 0x59, 0xaa, 0x6f, 0xb1, 0xd0, + 0x47, 0xf9, 0xfc, 0xa4, 0xed, 0x51, 0x9e, 0xa5, 0xd2, 0x1f, 0xe3, 0xba, 0x5b, 0x94, 0x34, 0xfe, 0xa1, 0x28, 0x3d, 0xfa, 0xd6, 0x3d, 0x01, 0x58, 0x9b, 0x0e, 0xb6, 0x1f, 0x24, 0x43, 0x51, 0xd0, + 0x33, 0x41, 0xdc, 0xd4, 0xdf, 0x62, 0x26, 0x5a, 0xfc, 0xae, 0xc6, 0x67, 0x6a, 0x87, 0x7d, 0x5c, 0xac, 0xb3, 0x59, 0xeb, 0xb5, 0x31, 0x96, 0x10, 0xdd, 0x44, 0x7d, 0xa9, 0x7e, 0x95, 0x0b, 0x0c, + }, + }, + { + .name = "Kyber Round 2, 1024 KAT 0 (PKCS#8/SPKI)", + .version = 0, + .keyform = 0, + .pk_len = 0, + .sk_len = 0, + .pkcs8_len = 4849, + .pkcs8 = { + 0x30, 0x82, 0x12, 0xed, 0x02, 0x01, 0x00, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x05, 0x04, 0x04, 0x05, 0x00, 0x04, 0x82, 0x12, 0xd5, 0x30, 0x82, 0x12, 0xd1, + 0x02, 0x01, 0x00, 0x03, 0x82, 0x0c, 0x61, 0x00, 0x07, 0x63, 0x8f, 0xb6, 0x98, 0x68, 0xf3, 0xd3, 0x20, 0xe5, 0x86, 0x2b, 0xd9, 0x69, 0x33, 0xfe, 0xb3, 0x11, 0xb3, 0x62, 0x09, 0x3c, 0x9b, 0x5d, + 0x50, 0x17, 0x0b, 0xce, 0xd4, 0x3f, 0x1b, 0x53, 0x6d, 0x9a, 0x20, 0x4b, 0xb1, 0xf2, 0x26, 0x95, 0x95, 0x0b, 0xa1, 0xf2, 0xa9, 0xe8, 0xeb, 0x82, 0x8b, 0x28, 0x44, 0x88, 0x76, 0x0b, 0x3f, 0xc8, + 0x4f, 0xab, 0xa0, 0x42, 0x75, 0xd5, 0x62, 0x8e, 0x39, 0xc5, 0xb2, 0x47, 0x13, 0x74, 0x28, 0x3c, 0x50, 0x32, 0x99, 0xc0, 0xab, 0x49, 0xb6, 0x6b, 0x8b, 0xbb, 0x56, 0xa4, 0x18, 0x66, 0x24, 0xf9, + 0x19, 0xa2, 0xba, 0x59, 0xbb, 0x08, 0xd8, 0x55, 0x18, 0x80, 0xc2, 0xbe, 0xfc, 0x4f, 0x87, 0xf2, 0x5f, 0x59, 0xab, 0x58, 0x7a, 0x79, 0xc3, 0x27, 0xd7, 0x92, 0xd5, 0x4c, 0x97, 0x4a, 0x69, 0x26, + 0x2f, 0xf8, 0xa7, 0x89, 0x38, 0x28, 0x9e, 0x9a, 0x87, 0xb6, 0x88, 0xb0, 0x83, 0xe0, 0x59, 0x5f, 0xe2, 0x18, 0xb6, 0xbb, 0x15, 0x05, 0x94, 0x1c, 0xe2, 0xe8, 0x1a, 0x5a, 0x64, 0xc5, 0xaa, 0xc6, + 0x04, 0x17, 0x25, 0x69, 0x85, 0x34, 0x9e, 0xe4, 0x7a, 0x52, 0x42, 0x0a, 0x5f, 0x97, 0x47, 0x7b, 0x72, 0x36, 0xac, 0x76, 0xbc, 0x70, 0xe8, 0x28, 0x87, 0x29, 0x28, 0x7e, 0xe3, 0xe3, 0x4a, 0x3d, + 0xbc, 0x36, 0x83, 0xc0, 0xb7, 0xb1, 0x00, 0x29, 0xfc, 0x20, 0x34, 0x18, 0x53, 0x7e, 0x74, 0x66, 0xba, 0x63, 0x85, 0xa8, 0xff, 0x30, 0x1e, 0xe1, 0x27, 0x08, 0xf8, 0x2a, 0xaa, 0x1e, 0x38, 0x0f, + 0xc7, 0xa8, 0x8f, 0x8f, 0x20, 0x5a, 0xb7, 0xe8, 0x8d, 0x7e, 0x95, 0x95, 0x2a, 0x55, 0xba, 0x20, 0xd0, 0x9b, 0x79, 0xa4, 0x71, 0x41, 0xd6, 0x2b, 0xf6, 0xeb, 0x7d, 0xd3, 0x07, 0xb0, 0x8e, 0xca, + 0x13, 0xa5, 0xbc, 0x5f, 0x6b, 0x68, 0x58, 0x1c, 0x68, 0x65, 0xb2, 0x7b, 0xbc, 0xdd, 0xab, 0x14, 0x2f, 0x4b, 0x2c, 0xbf, 0xf4, 0x88, 0xc8, 0xa2, 0x27, 0x05, 0xfa, 0xa9, 0x8a, 0x2b, 0x9e, 0xea, + 0x35, 0x30, 0xc7, 0x66, 0x62, 0x33, 0x5c, 0xc7, 0xea, 0x3a, 0x00, 0x77, 0x77, 0x25, 0xeb, 0xcc, 0xcd, 0x2a, 0x46, 0x36, 0xb2, 0xd9, 0x12, 0x2f, 0xf3, 0xab, 0x77, 0x12, 0x3c, 0xe0, 0x88, 0x3c, + 0x19, 0x11, 0x11, 0x5e, 0x50, 0xc9, 0xe8, 0xa9, 0x41, 0x94, 0xe4, 0x8d, 0xd0, 0xd0, 0x9c, 0xff, 0xb3, 0xad, 0xcd, 0x2c, 0x1e, 0x92, 0x43, 0x09, 0x03, 0xd0, 0x7a, 0xdb, 0xf0, 0x05, 0x32, 0x03, + 0x15, 0x75, 0xaa, 0x7f, 0x9e, 0x7b, 0x5a, 0x1f, 0x33, 0x62, 0xde, 0xc9, 0x36, 0xd4, 0x04, 0x3c, 0x05, 0xf2, 0x47, 0x6c, 0x07, 0x57, 0x8b, 0xc9, 0xcb, 0xaf, 0x2a, 0xb4, 0xe3, 0x82, 0x72, 0x7a, + 0xd4, 0x16, 0x86, 0xa9, 0x6b, 0x25, 0x48, 0x82, 0x0b, 0xb0, 0x3b, 0x32, 0xf1, 0x1b, 0x28, 0x11, 0xad, 0x62, 0xf4, 0x89, 0xe9, 0x51, 0x63, 0x2a, 0xba, 0x0d, 0x1d, 0xf8, 0x96, 0x80, 0xcc, 0x8a, + 0x8b, 0x53, 0xb4, 0x81, 0xd9, 0x2a, 0x68, 0xd7, 0x0b, 0x4e, 0xa1, 0xc3, 0xa6, 0xa5, 0x61, 0xc0, 0x69, 0x28, 0x82, 0xb5, 0xca, 0x8c, 0xc9, 0x42, 0xa8, 0xd4, 0x95, 0xaf, 0xcb, 0x06, 0xde, 0x89, + 0x49, 0x8f, 0xb9, 0x35, 0xb7, 0x75, 0x90, 0x8f, 0xe7, 0xa0, 0x3e, 0x32, 0x4d, 0x54, 0xcc, 0x19, 0xd4, 0xe1, 0xaa, 0xbd, 0x35, 0x93, 0xb3, 0x8b, 0x19, 0xee, 0x13, 0x88, 0xfe, 0x49, 0x2b, 0x43, + 0x12, 0x7e, 0x5a, 0x50, 0x42, 0x53, 0x78, 0x6a, 0x0d, 0x69, 0xad, 0x32, 0x60, 0x1c, 0x28, 0xe2, 0xc8, 0x85, 0x04, 0xa5, 0xba, 0x59, 0x97, 0x06, 0x02, 0x3a, 0x61, 0x36, 0x3e, 0x17, 0xc6, 0xb9, + 0xbb, 0x59, 0xbd, 0xc6, 0x97, 0x45, 0x2c, 0xd0, 0x59, 0x45, 0x19, 0x83, 0xd7, 0x38, 0xca, 0x3f, 0xd0, 0x34, 0xe3, 0xf5, 0x98, 0x88, 0x54, 0xca, 0x05, 0x03, 0x1d, 0xb0, 0x96, 0x11, 0x49, 0x89, + 0x88, 0x19, 0x7c, 0x6b, 0x30, 0xd2, 0x58, 0xdf, 0xe2, 0x62, 0x65, 0x54, 0x1c, 0x89, 0xa4, 0xb3, 0x1d, 0x68, 0x64, 0xe9, 0x38, 0x9b, 0x03, 0xcb, 0x74, 0xf7, 0xec, 0x43, 0x23, 0xfb, 0x94, 0x21, + 0xa4, 0xb9, 0x79, 0x0a, 0x26, 0xd1, 0x7b, 0x03, 0x98, 0xa2, 0x67, 0x67, 0x35, 0x09, 0x09, 0xf8, 0x4d, 0x57, 0xb6, 0x69, 0x4d, 0xf8, 0x30, 0x66, 0x4c, 0xa8, 0xb3, 0xc3, 0xc0, 0x3e, 0xd2, 0xae, + 0x67, 0xb8, 0x90, 0x06, 0x86, 0x8a, 0x68, 0x52, 0x7c, 0xcd, 0x66, 0x64, 0x59, 0xab, 0x7f, 0x05, 0x66, 0x71, 0x00, 0x0c, 0x61, 0x64, 0xd3, 0xa7, 0xf2, 0x66, 0xa1, 0x4d, 0x97, 0xcb, 0xd7, 0x00, + 0x4d, 0x6c, 0x92, 0xca, 0xca, 0x77, 0x0b, 0x84, 0x4a, 0x4f, 0xa9, 0xb1, 0x82, 0xe7, 0xb1, 0x8c, 0xa8, 0x85, 0x08, 0x2a, 0xc5, 0x64, 0x6f, 0xcb, 0x4a, 0x14, 0xe1, 0x68, 0x5f, 0xeb, 0x0c, 0x9c, + 0xe3, 0x37, 0x2a, 0xb9, 0x53, 0x65, 0xc0, 0x4f, 0xd8, 0x30, 0x84, 0xf8, 0x0a, 0x23, 0xff, 0x10, 0xa0, 0x5b, 0xf1, 0x5f, 0x7f, 0xa5, 0xac, 0xc6, 0xc0, 0xcb, 0x46, 0x2c, 0x33, 0xca, 0x52, 0x4f, + 0xa6, 0xb8, 0xbb, 0x35, 0x90, 0x43, 0xba, 0x68, 0x60, 0x9e, 0xaa, 0x25, 0x36, 0xe8, 0x1d, 0x08, 0x46, 0x3b, 0x19, 0x65, 0x3b, 0x54, 0x35, 0xba, 0x94, 0x6c, 0x9a, 0xdd, 0xeb, 0x20, 0x2b, 0x04, + 0xb0, 0x31, 0xcc, 0x96, 0x0d, 0xcc, 0x12, 0xe4, 0x51, 0x8d, 0x42, 0x8b, 0x32, 0xb2, 0x57, 0xa4, 0xfc, 0x73, 0x13, 0xd3, 0xa7, 0x98, 0x0d, 0x80, 0x08, 0x2e, 0x93, 0x4f, 0x9d, 0x95, 0xc3, 0x2b, + 0x0a, 0x01, 0x91, 0xa2, 0x36, 0x04, 0x38, 0x4d, 0xd9, 0xe0, 0x79, 0xbb, 0xba, 0xa2, 0x66, 0xd1, 0x4c, 0x3f, 0x75, 0x6b, 0x9f, 0x21, 0x33, 0x10, 0x74, 0x33, 0xa4, 0xe8, 0x3f, 0xa7, 0x18, 0x72, + 0x82, 0xa8, 0x09, 0x20, 0x3a, 0x4f, 0xaf, 0x84, 0x18, 0x51, 0x83, 0x3d, 0x12, 0x1a, 0xc3, 0x83, 0x84, 0x3a, 0x5e, 0x55, 0xbc, 0x23, 0x81, 0x42, 0x5e, 0x16, 0xc7, 0xdb, 0x4c, 0xc9, 0xab, 0x5c, + 0x1b, 0x0d, 0x91, 0xa4, 0x7e, 0x2b, 0x8d, 0xe0, 0xe5, 0x82, 0xc8, 0x6b, 0x6b, 0x0d, 0x90, 0x7b, 0xb3, 0x60, 0xb9, 0x7f, 0x40, 0xab, 0x5d, 0x03, 0x8f, 0x6b, 0x75, 0xc8, 0x14, 0xb2, 0x7d, 0x9b, + 0x96, 0x8d, 0x41, 0x98, 0x32, 0xbc, 0x8c, 0x2b, 0xee, 0x60, 0x5e, 0xf6, 0xe5, 0x05, 0x9d, 0x33, 0x10, 0x0d, 0x90, 0x48, 0x5d, 0x37, 0x84, 0x50, 0x01, 0x42, 0x21, 0x73, 0x6c, 0x07, 0x40, 0x7c, + 0xac, 0x26, 0x04, 0x08, 0xaa, 0x64, 0x92, 0x66, 0x19, 0x78, 0x8b, 0x86, 0x01, 0xc2, 0xa7, 0x52, 0xd1, 0xa6, 0xcb, 0xf8, 0x20, 0xd7, 0xc7, 0xa0, 0x47, 0x16, 0x20, 0x32, 0x25, 0xb3, 0x89, 0x5b, + 0x93, 0x42, 0xd1, 0x47, 0xa8, 0x18, 0x5c, 0xfc, 0x1b, 0xb6, 0x5b, 0xa0, 0x6b, 0x41, 0x42, 0x33, 0x99, 0x03, 0xc0, 0xac, 0x46, 0x51, 0x38, 0x5b, 0x45, 0xd9, 0x8a, 0x8b, 0x19, 0xd2, 0x8c, 0xd6, + 0xba, 0xb0, 0x88, 0x78, 0x7f, 0x7e, 0xe1, 0xb1, 0x24, 0x61, 0x76, 0x6b, 0x43, 0xcb, 0xcc, 0xb9, 0x64, 0x34, 0x42, 0x7d, 0x93, 0xc0, 0x65, 0x55, 0x06, 0x88, 0xf6, 0x94, 0x8e, 0xd1, 0xb5, 0x47, + 0x5a, 0x42, 0x5f, 0x1b, 0x85, 0x20, 0x9d, 0x06, 0x1c, 0x08, 0xb5, 0x6c, 0x1c, 0xc0, 0x69, 0xf6, 0xc0, 0xa7, 0xc6, 0xf2, 0x93, 0x58, 0xca, 0xb9, 0x11, 0x08, 0x77, 0x32, 0xa6, 0x49, 0xd2, 0x7c, + 0x9b, 0x98, 0xf9, 0xa4, 0x88, 0x79, 0x38, 0x7d, 0x9b, 0x00, 0xc2, 0x59, 0x59, 0xa7, 0x16, 0x54, 0xd6, 0xf6, 0xa9, 0x46, 0x16, 0x45, 0x13, 0xe4, 0x7a, 0x75, 0xd0, 0x05, 0x98, 0x6c, 0x23, 0x63, + 0xc0, 0x9f, 0x6b, 0x53, 0x7e, 0xca, 0x78, 0xb9, 0x30, 0x3a, 0x5f, 0xa4, 0x57, 0x60, 0x8a, 0x58, 0x6a, 0x65, 0x3a, 0x34, 0x7d, 0xb0, 0x4d, 0xfc, 0xc1, 0x91, 0x75, 0xb3, 0xa3, 0x01, 0x17, 0x25, + 0x36, 0x06, 0x2a, 0x65, 0x8a, 0x95, 0x27, 0x75, 0x70, 0xc8, 0x85, 0x2c, 0xa8, 0x97, 0x3f, 0x4a, 0xe1, 0x23, 0xa3, 0x34, 0x04, 0x7d, 0xd7, 0x11, 0xc8, 0x92, 0x7a, 0x63, 0x4a, 0x03, 0x38, 0x8a, + 0x52, 0x7b, 0x03, 0x4b, 0xf7, 0xa8, 0x17, 0x0f, 0xa7, 0x02, 0xc1, 0xf7, 0xc2, 0x3e, 0xc3, 0x2d, 0x18, 0xa2, 0x37, 0x48, 0x90, 0xbe, 0x9c, 0x78, 0x7a, 0x94, 0x09, 0xc8, 0x2d, 0x19, 0x2c, 0x4b, + 0xb7, 0x05, 0xa2, 0xf9, 0x96, 0xce, 0x40, 0x5d, 0x85, 0xa4, 0xc1, 0xa1, 0xab, 0x9b, 0x6a, 0xeb, 0x49, 0xcc, 0xe1, 0xc2, 0xf8, 0xa9, 0x7c, 0x35, 0x16, 0xc7, 0x2a, 0x00, 0xa4, 0x62, 0x63, 0xba, + 0xa6, 0x96, 0xbf, 0x25, 0x72, 0x77, 0x19, 0xc3, 0x21, 0x64, 0x23, 0x61, 0x8f, 0xf3, 0x33, 0x80, 0x93, 0x4a, 0x6c, 0x10, 0x54, 0x5c, 0x4c, 0x5c, 0x51, 0x55, 0xb1, 0x24, 0x86, 0x18, 0x1f, 0xc7, + 0xa2, 0x31, 0x98, 0x73, 0x97, 0x8b, 0x6a, 0x2a, 0x67, 0x49, 0x0f, 0x82, 0x56, 0xbd, 0x21, 0x96, 0xfe, 0x17, 0x92, 0xa4, 0xc0, 0x00, 0x77, 0xb8, 0x12, 0xea, 0xe8, 0xbe, 0xd3, 0x57, 0x24, 0x99, + 0x68, 0x4a, 0xb3, 0x37, 0x18, 0x76, 0x76, 0x1e, 0x45, 0x0c, 0x9f, 0x9d, 0x27, 0x68, 0xa3, 0x68, 0x06, 0xd7, 0xab, 0x20, 0x46, 0xc9, 0x1f, 0x17, 0x59, 0x9e, 0x9a, 0xc5, 0x92, 0x99, 0x08, 0x08, + 0xdc, 0xd7, 0xb4, 0xd0, 0x91, 0x90, 0x72, 0xf1, 0x4e, 0xc3, 0x61, 0x77, 0x3b, 0x72, 0x52, 0x44, 0x4c, 0x32, 0x3c, 0x30, 0x83, 0x26, 0xf4, 0xa3, 0x0f, 0x86, 0x80, 0xd2, 0xf7, 0x48, 0xf5, 0x6a, + 0x13, 0x2b, 0x82, 0x67, 0x4e, 0xd0, 0x18, 0x46, 0x20, 0xb8, 0x2a, 0xd2, 0xcb, 0x18, 0x2c, 0x97, 0xb4, 0x81, 0x62, 0x66, 0x47, 0x49, 0x12, 0x90, 0xa0, 0x11, 0xcc, 0x73, 0x82, 0x86, 0x85, 0xa8, + 0xc3, 0x67, 0xa5, 0xb9, 0xcf, 0x8d, 0x62, 0x1b, 0x0d, 0x5c, 0x1e, 0xff, 0x03, 0x17, 0x27, 0x58, 0xbd, 0x00, 0x49, 0x78, 0xc2, 0x51, 0xcd, 0x51, 0x34, 0x22, 0x28, 0x98, 0x9c, 0xae, 0x63, 0x32, + 0xac, 0x48, 0x64, 0x37, 0xcb, 0x5c, 0x57, 0xd4, 0x30, 0x74, 0x62, 0x86, 0x52, 0x53, 0xbe, 0x21, 0x7b, 0x35, 0x15, 0xc7, 0x3d, 0xf4, 0x05, 0xb7, 0xf2, 0x82, 0x17, 0xad, 0x0b, 0x8c, 0xf6, 0x0c, + 0x2f, 0xff, 0xaa, 0x0a, 0x00, 0x48, 0xb1, 0xfb, 0x4a, 0xcd, 0xcd, 0xc3, 0x8b, 0x52, 0x50, 0xcf, 0xec, 0x35, 0x6a, 0x6d, 0xe2, 0x6c, 0xfa, 0x7a, 0x58, 0x8f, 0xdc, 0x86, 0xf9, 0x8c, 0x85, 0x4a, + 0xc6, 0x4c, 0x7b, 0xfa, 0xa9, 0x6f, 0x5a, 0x32, 0xcc, 0x06, 0x10, 0x93, 0x4b, 0xaa, 0x6a, 0x58, 0x6b, 0x9a, 0x20, 0x54, 0xf1, 0x3b, 0xa2, 0x74, 0x17, 0x4a, 0xa0, 0xd2, 0xb3, 0xa8, 0x1b, 0x96, + 0xa9, 0x40, 0x66, 0x6f, 0x78, 0x9b, 0x5a, 0x6b, 0xcd, 0xc0, 0xa6, 0xa0, 0x17, 0x8a, 0x0c, 0x9a, 0x02, 0x57, 0x8a, 0x49, 0x3f, 0x6e, 0xea, 0x0d, 0x2e, 0x6c, 0x13, 0x95, 0x1c, 0x9f, 0x24, 0x9a, + 0x5e, 0x8d, 0xd7, 0x1d, 0xd4, 0x9a, 0x74, 0x2d, 0x45, 0x1f, 0x1a, 0xbb, 0xa1, 0x9a, 0xf8, 0xc5, 0x47, 0x85, 0x5e, 0x0a, 0xfc, 0x72, 0x8e, 0x90, 0xab, 0xb4, 0x99, 0xc9, 0xbe, 0xeb, 0x76, 0x6f, + 0x47, 0x29, 0xcd, 0xa2, 0x22, 0x63, 0xe3, 0x24, 0xda, 0x18, 0x71, 0x2d, 0x31, 0x6e, 0x98, 0xdc, 0x7a, 0xc8, 0xc3, 0xca, 0x47, 0x37, 0x0e, 0xbd, 0x77, 0x0c, 0xe3, 0x2b, 0x3b, 0xd4, 0xb1, 0xa0, + 0xc9, 0x52, 0x9a, 0xc6, 0xec, 0x8e, 0xe0, 0x28, 0xb1, 0xcd, 0xb2, 0x65, 0x1c, 0xb5, 0xa6, 0xbb, 0x3c, 0x0c, 0x6d, 0xf1, 0x24, 0x0a, 0x3b, 0x91, 0x4b, 0x56, 0x56, 0xc0, 0xdc, 0x51, 0xc2, 0xb9, + 0x1b, 0xfc, 0xbc, 0x37, 0xa4, 0x66, 0x02, 0x87, 0xd4, 0x4f, 0x81, 0xf8, 0x53, 0xc7, 0xf4, 0x9a, 0x6d, 0x06, 0x03, 0xd6, 0xd7, 0x23, 0xcb, 0xec, 0x01, 0x5f, 0xbc, 0x43, 0x4a, 0x38, 0x24, 0x1c, + 0x10, 0x9c, 0x7e, 0xd5, 0xb1, 0xcc, 0x46, 0x1a, 0x2c, 0xcb, 0x9a, 0xb7, 0x14, 0x0f, 0x19, 0xf3, 0x7a, 0x13, 0xbb, 0x70, 0x1e, 0x14, 0x2b, 0xd5, 0x4b, 0x64, 0xec, 0x6b, 0x76, 0xfe, 0xc3, 0x3b, + 0x69, 0xc2, 0x91, 0x8c, 0xb0, 0x17, 0xc4, 0x14, 0x34, 0x23, 0x00, 0x9a, 0x3c, 0x07, 0xb5, 0xc1, 0x81, 0xb0, 0xc1, 0xeb, 0x49, 0x4a, 0x62, 0xab, 0xc8, 0x39, 0x13, 0x97, 0x08, 0x9e, 0xa6, 0x64, + 0x09, 0x67, 0xc1, 0x20, 0x49, 0x84, 0xcd, 0x48, 0x4c, 0xcc, 0xb0, 0x0a, 0x9a, 0x17, 0xd0, 0x87, 0x21, 0x84, 0x28, 0xef, 0x3b, 0xb7, 0x08, 0x78, 0x3e, 0x12, 0x82, 0x71, 0x04, 0x41, 0x73, 0x75, + 0xb6, 0x95, 0x6f, 0xb5, 0x00, 0x53, 0xd0, 0x48, 0xa4, 0x79, 0x14, 0x95, 0x82, 0x4a, 0x34, 0x80, 0xa5, 0xb7, 0x83, 0x02, 0x56, 0x09, 0x6f, 0xdd, 0x72, 0x5c, 0x30, 0x8b, 0x3b, 0xe8, 0x4a, 0x07, + 0xf3, 0x63, 0x2e, 0x24, 0x95, 0xc6, 0x2e, 0x96, 0x39, 0x9d, 0x80, 0xbf, 0xa7, 0x45, 0xb9, 0x84, 0x1a, 0x18, 0x33, 0xbc, 0x1d, 0x27, 0xba, 0x45, 0xa5, 0x21, 0x68, 0xee, 0x59, 0x00, 0x6c, 0x3a, + 0x3a, 0x8c, 0x4a, 0x5a, 0x4f, 0x50, 0x88, 0xfc, 0x73, 0x71, 0x81, 0xab, 0x51, 0x96, 0xf7, 0xb1, 0xb4, 0x9a, 0x2e, 0xd8, 0x13, 0x13, 0x4e, 0x11, 0x2f, 0x73, 0x0b, 0x99, 0x1c, 0x54, 0xa7, 0x19, + 0x6b, 0xcf, 0x5f, 0xc7, 0x6e, 0x13, 0x4c, 0x58, 0x43, 0xe1, 0x69, 0x88, 0x51, 0xb2, 0xf8, 0x69, 0xaf, 0xaf, 0xb0, 0x27, 0x87, 0xd9, 0xc2, 0xf1, 0x36, 0x90, 0x2d, 0xc7, 0xa7, 0xf3, 0xd6, 0x21, + 0x56, 0xd1, 0x5e, 0xc3, 0x09, 0x56, 0x40, 0x92, 0xc6, 0x1d, 0x83, 0xb0, 0x98, 0x6c, 0x48, 0x40, 0x99, 0x81, 0xf3, 0xc1, 0x86, 0x88, 0x0a, 0x2f, 0x63, 0xd5, 0x86, 0x0a, 0xb6, 0x01, 0xde, 0xac, + 0x2b, 0x6b, 0xa1, 0xb4, 0x28, 0x17, 0x9d, 0x73, 0x53, 0x3e, 0xb7, 0xa3, 0xa5, 0x11, 0x3b, 0x85, 0x61, 0xf1, 0x0b, 0x45, 0xc3, 0xcd, 0xe2, 0x82, 0xb6, 0xea, 0xd6, 0xab, 0x6c, 0x60, 0x4f, 0x09, + 0xc1, 0x7b, 0xfd, 0xa0, 0x83, 0x13, 0xa3, 0x26, 0x07, 0x67, 0x5a, 0xdf, 0x64, 0x31, 0xca, 0x87, 0x18, 0xe9, 0xc4, 0x3a, 0x73, 0x73, 0x32, 0x27, 0xe7, 0x3b, 0xc6, 0x1a, 0xc8, 0x45, 0xba, 0x90, + 0x77, 0x55, 0xce, 0xc6, 0x89, 0x25, 0xe5, 0xe2, 0xbf, 0xe9, 0x12, 0x95, 0x9d, 0xb8, 0x6f, 0xbf, 0xe2, 0x15, 0x6f, 0xd5, 0xbb, 0xdb, 0xf0, 0xc9, 0xdf, 0x8b, 0x53, 0x02, 0xaa, 0x8d, 0x90, 0xa2, + 0x2d, 0x12, 0x27, 0x0e, 0x00, 0x65, 0x51, 0xe4, 0x76, 0x7e, 0x45, 0x26, 0x8e, 0xd9, 0x69, 0x26, 0x54, 0x44, 0x78, 0x11, 0xea, 0xb8, 0x4f, 0x04, 0x99, 0xa8, 0xa5, 0x8c, 0xf7, 0xc0, 0x4a, 0x59, + 0x56, 0x98, 0x52, 0x80, 0x45, 0xf2, 0x98, 0x97, 0xc8, 0xfa, 0x96, 0xd0, 0x6c, 0xce, 0x51, 0xe6, 0xaf, 0xea, 0xc4, 0x33, 0x95, 0x89, 0xc9, 0x41, 0xc8, 0x55, 0x63, 0xd7, 0x0f, 0xac, 0xe1, 0x92, + 0x88, 0x94, 0xba, 0xc0, 0x36, 0x19, 0xdf, 0xf4, 0xbe, 0x3f, 0x43, 0x14, 0xa3, 0xf7, 0x35, 0x1a, 0x09, 0xa4, 0x86, 0xb5, 0x04, 0x1e, 0x7c, 0xb2, 0xda, 0x8b, 0x96, 0xbc, 0x66, 0x26, 0xa4, 0x93, + 0x17, 0x35, 0x7c, 0x41, 0x52, 0xa5, 0x1b, 0xa3, 0xc2, 0x8c, 0x7e, 0x0c, 0x9d, 0xb4, 0x1a, 0x06, 0xa2, 0x82, 0x90, 0xf2, 0x18, 0x73, 0x11, 0x07, 0xc9, 0x54, 0xd8, 0xa6, 0x6f, 0x80, 0x1d, 0x7d, + 0xe1, 0x2a, 0x03, 0x71, 0x16, 0x99, 0x0b, 0x6c, 0x53, 0xc1, 0x29, 0xf1, 0x85, 0xc3, 0x45, 0xf2, 0x7e, 0x51, 0x8b, 0x2d, 0x5a, 0x91, 0x25, 0xa0, 0x70, 0x76, 0xd9, 0x91, 0xb7, 0xda, 0xc7, 0xcc, + 0x65, 0xa8, 0x56, 0x2e, 0xfb, 0xcc, 0x32, 0xa9, 0xca, 0x4a, 0xd9, 0x02, 0x63, 0xb0, 0x4a, 0x4f, 0x90, 0x36, 0x11, 0x6c, 0x7b, 0x97, 0x48, 0x04, 0x96, 0x31, 0x75, 0x75, 0x65, 0x0d, 0xcc, 0x21, + 0x52, 0xb5, 0xbc, 0x0e, 0x74, 0x40, 0x7e, 0x12, 0xfa, 0x8e, 0x4f, 0xfc, 0xcc, 0xff, 0x76, 0xc0, 0x1a, 0x97, 0x4b, 0xd6, 0x11, 0x02, 0xe1, 0xf5, 0x29, 0x64, 0x96, 0xc7, 0x1d, 0x07, 0x64, 0xe1, + 0x32, 0x29, 0xff, 0xe7, 0x84, 0x6f, 0x33, 0x6e, 0x34, 0xca, 0xc9, 0x04, 0xca, 0x56, 0x70, 0xf8, 0xcd, 0x50, 0x52, 0x42, 0x7a, 0x79, 0xc0, 0x91, 0xa9, 0x71, 0x21, 0x0c, 0x5c, 0xff, 0x66, 0x7a, + 0xac, 0x24, 0x93, 0x66, 0xe1, 0x0d, 0x2b, 0x11, 0x37, 0x6c, 0xa3, 0x9d, 0x93, 0x52, 0x04, 0xb1, 0x2c, 0xc5, 0x85, 0xe9, 0x40, 0x54, 0x03, 0x62, 0x5f, 0xb3, 0x2c, 0xb5, 0xe5, 0xc3, 0x1b, 0x62, + 0x34, 0x81, 0x60, 0x51, 0x5c, 0xcc, 0x4f, 0xda, 0xf5, 0x70, 0x2d, 0x6b, 0xab, 0x5c, 0x37, 0x3d, 0xb6, 0xf3, 0x50, 0xd3, 0xe6, 0x3a, 0x5c, 0xe3, 0xca, 0x54, 0x74, 0xa0, 0xcf, 0x15, 0x67, 0x04, + 0x2c, 0xa3, 0x25, 0x89, 0x86, 0xff, 0x75, 0xbd, 0xfc, 0xd9, 0x29, 0xe6, 0x46, 0x2f, 0x36, 0xbc, 0xcc, 0x3f, 0x5a, 0x93, 0x35, 0x2a, 0x2b, 0x36, 0xcb, 0x16, 0x2e, 0x18, 0x74, 0xc7, 0x42, 0x87, + 0x0a, 0x97, 0xb1, 0x67, 0xa0, 0x50, 0x37, 0x36, 0x24, 0xea, 0xeb, 0x7e, 0x50, 0x73, 0x25, 0x6b, 0x72, 0x11, 0xb2, 0xd9, 0x4b, 0x84, 0x06, 0xcd, 0x6c, 0x95, 0x33, 0xb1, 0x53, 0x64, 0x08, 0xab, + 0x0a, 0x29, 0xe5, 0xb2, 0xf0, 0xc9, 0x54, 0xec, 0xe0, 0x0f, 0xbb, 0xeb, 0x17, 0x6d, 0x72, 0x4d, 0x4c, 0xf4, 0x43, 0xcf, 0x70, 0x20, 0xd5, 0xfa, 0x70, 0x94, 0xcc, 0x1b, 0x1b, 0xe6, 0x97, 0xba, + 0xd3, 0x36, 0x74, 0xe4, 0x09, 0x9e, 0xc7, 0xbb, 0x18, 0xf4, 0x57, 0x71, 0x28, 0xcd, 0xd9, 0x7c, 0xcd, 0x6d, 0x44, 0x62, 0xe5, 0x60, 0x7c, 0x51, 0x2a, 0x3e, 0x36, 0x24, 0x8e, 0x3d, 0xda, 0xa2, + 0xec, 0x08, 0x9a, 0xef, 0xc4, 0xce, 0x48, 0x5c, 0x49, 0xd7, 0xb0, 0x09, 0xc8, 0xd6, 0x31, 0x15, 0xfc, 0x81, 0xff, 0x3a, 0x62, 0xd1, 0x5a, 0x88, 0x44, 0x1c, 0x03, 0xea, 0x1c, 0x2e, 0x72, 0xc4, + 0x88, 0x39, 0xfc, 0x6a, 0xd7, 0x3a, 0x30, 0x74, 0x4a, 0x62, 0xb7, 0xb2, 0x16, 0x45, 0xa6, 0xaf, 0x7d, 0x61, 0xb6, 0x38, 0x3b, 0x22, 0x1e, 0x21, 0x90, 0x55, 0x57, 0xcd, 0x29, 0xd9, 0x24, 0xa6, + 0x09, 0x86, 0xc5, 0x11, 0xc1, 0xeb, 0xbc, 0x31, 0x6d, 0x56, 0x30, 0xa2, 0x41, 0x43, 0x23, 0xf5, 0x3a, 0xd5, 0x59, 0x94, 0xf6, 0xb3, 0x65, 0x39, 0xf9, 0xc4, 0x40, 0x75, 0xa5, 0x33, 0xe4, 0x81, + 0xc0, 0x84, 0x45, 0xd9, 0xca, 0x9e, 0x9d, 0x38, 0x21, 0x19, 0x38, 0x8b, 0xd1, 0xd7, 0x50, 0x52, 0x21, 0x7a, 0x94, 0x4c, 0xcc, 0x7b, 0xe9, 0x09, 0xe2, 0x19, 0x71, 0x1f, 0xcc, 0x79, 0x24, 0x76, + 0x92, 0x13, 0xa1, 0x92, 0x53, 0x4a, 0x55, 0x80, 0x08, 0x15, 0x7a, 0x39, 0x6e, 0xdf, 0xf4, 0x80, 0xcc, 0x3b, 0x52, 0x0f, 0xf8, 0x18, 0xb3, 0x8b, 0x13, 0x5c, 0x18, 0xa8, 0x0d, 0x51, 0x05, 0xe6, + 0x78, 0x83, 0x6c, 0x39, 0x5c, 0x28, 0xe9, 0x2f, 0x7a, 0x3c, 0x4e, 0x93, 0xc0, 0x10, 0x35, 0xf3, 0x41, 0x11, 0xcc, 0x49, 0x02, 0xd0, 0xc0, 0x33, 0xa6, 0x3f, 0x23, 0x6a, 0x71, 0xda, 0x97, 0x4a, + 0x6f, 0x40, 0x4f, 0x7a, 0xa7, 0xb5, 0xe5, 0x82, 0xc7, 0x58, 0x14, 0x2f, 0xc1, 0x82, 0x6b, 0xba, 0x98, 0xb2, 0x7d, 0x57, 0xc2, 0xe2, 0x10, 0x3e, 0x10, 0xe3, 0x0d, 0x32, 0x79, 0x7b, 0x96, 0x77, + 0x14, 0xd1, 0x56, 0x61, 0x11, 0x13, 0x71, 0xa2, 0xd9, 0xc5, 0x39, 0x98, 0x12, 0x46, 0x46, 0x22, 0x63, 0x5b, 0x44, 0x21, 0x26, 0xb0, 0x98, 0x36, 0xb0, 0x81, 0x82, 0x72, 0x47, 0xd0, 0x54, 0x22, + 0x97, 0x2b, 0xd0, 0x32, 0x0d, 0x8f, 0x42, 0xbf, 0x57, 0xe3, 0x49, 0x46, 0x12, 0x34, 0xe4, 0xd9, 0x4f, 0x01, 0x18, 0x50, 0xba, 0xb5, 0xc0, 0x49, 0xb6, 0x2a, 0x59, 0x43, 0x38, 0x66, 0xfc, 0xce, + 0x69, 0x66, 0x49, 0x5c, 0x26, 0x5c, 0x47, 0x65, 0xa5, 0x6c, 0x06, 0xb9, 0xfc, 0x42, 0x76, 0x54, 0x87, 0x85, 0xf4, 0x68, 0x28, 0xca, 0x60, 0x2d, 0xc6, 0xd0, 0x54, 0x1f, 0x25, 0x07, 0x89, 0xc4, + 0x9e, 0x8b, 0x06, 0x55, 0x9c, 0x43, 0x44, 0x60, 0xa8, 0x43, 0x80, 0x98, 0x54, 0xe5, 0xb4, 0x6e, 0x89, 0x38, 0x9f, 0x10, 0xf4, 0x89, 0x66, 0x74, 0x91, 0xc1, 0x93, 0x5e, 0x8a, 0xfb, 0x9e, 0xb4, + 0x71, 0x8f, 0x86, 0xac, 0x45, 0x89, 0x32, 0xbc, 0xf3, 0x3c, 0x9a, 0xbe, 0xcb, 0x2d, 0xc0, 0xc0, 0x93, 0xa7, 0xe8, 0x1d, 0xa0, 0x32, 0x7b, 0xb6, 0x37, 0x52, 0x81, 0x05, 0xc3, 0x58, 0xeb, 0x76, + 0x8d, 0x32, 0x3a, 0x37, 0xd4, 0x0a, 0x8c, 0x19, 0x9b, 0x7c, 0x4b, 0xb1, 0xd7, 0x2b, 0x72, 0xb6, 0x90, 0xb3, 0x6d, 0xd2, 0x7a, 0x93, 0x55, 0x19, 0x1b, 0x3c, 0x3a, 0xa6, 0x75, 0xa7, 0xe6, 0xf8, + 0x55, 0xeb, 0x50, 0x5f, 0x57, 0x98, 0x65, 0xdb, 0xd8, 0x91, 0x05, 0x65, 0x50, 0x5e, 0x7c, 0x0f, 0xdd, 0x54, 0x5c, 0xbb, 0xb8, 0x71, 0xb0, 0xb2, 0xcc, 0x01, 0x25, 0xb7, 0x4f, 0x6b, 0x0c, 0x9b, + 0x79, 0x67, 0x0a, 0x62, 0x02, 0xd1, 0xb9, 0x15, 0x4a, 0xc7, 0x76, 0x6b, 0x19, 0x19, 0xc4, 0x89, 0x58, 0x90, 0x86, 0xad, 0x8b, 0x45, 0xbe, 0x0d, 0x79, 0xc9, 0x76, 0xc3, 0xc3, 0x9d, 0x6b, 0x25, + 0x21, 0x3b, 0xb0, 0xb7, 0x8a, 0x57, 0x50, 0xe6, 0xa8, 0xeb, 0x34, 0x33, 0x0b, 0xb3, 0xcf, 0xf2, 0xb1, 0xc0, 0x72, 0x2a, 0xc8, 0x83, 0xb0, 0x48, 0xf4, 0xb8, 0xcd, 0x06, 0x19, 0x6d, 0xa8, 0xaa, + 0x8b, 0x05, 0xda, 0x42, 0x67, 0x55, 0x2b, 0xf8, 0x7a, 0xbc, 0xa5, 0x12, 0x4d, 0xc3, 0x58, 0xa8, 0x38, 0x10, 0x40, 0xe9, 0xb8, 0x1f, 0xb0, 0x84, 0x43, 0x15, 0x02, 0x15, 0xd6, 0x92, 0x23, 0x28, + 0x00, 0x0a, 0xc0, 0xb7, 0x88, 0xb1, 0x21, 0x93, 0x1a, 0x26, 0x7d, 0x80, 0x61, 0x9c, 0xe7, 0xd2, 0x9c, 0xd7, 0x6b, 0x60, 0xcf, 0x65, 0x83, 0xdc, 0xe8, 0xce, 0xbc, 0x49, 0x01, 0x85, 0x73, 0x6c, + 0x81, 0x8b, 0x25, 0xad, 0x26, 0x0b, 0x66, 0x7b, 0x1f, 0xfd, 0x46, 0x20, 0x6d, 0x01, 0x04, 0x55, 0x3a, 0xa9, 0xfb, 0x30, 0x45, 0x54, 0xa2, 0x1c, 0x32, 0x72, 0x44, 0xce, 0x78, 0xaf, 0xdb, 0xd3, + 0xb4, 0x62, 0x36, 0x1b, 0xb0, 0x68, 0xa1, 0x55, 0x63, 0x64, 0x09, 0xf5, 0x74, 0xc5, 0x71, 0x65, 0x72, 0xe2, 0xa5, 0xf2, 0xa4, 0xb0, 0x4f, 0xb8, 0xaa, 0xd1, 0x23, 0x66, 0x84, 0x84, 0x17, 0x87, + 0x56, 0x2a, 0xaf, 0x46, 0xc2, 0xc0, 0xda, 0x46, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, + 0x54, 0xa3, 0x16, 0x65, 0x29, 0xb5, 0x39, 0x22, 0xa5, 0x89, 0x9a, 0x0b, 0xc4, 0x65, 0xee, 0x5f, 0xc2, 0xc0, 0x41, 0x55, 0x58, 0x2a, 0x40, 0xac, 0x70, 0x97, 0x61, 0xd2, 0xbe, 0x61, 0xfd, 0xc7, + 0x6c, 0x59, 0x30, 0x44, 0xce, 0xbc, 0xc7, 0xf2, 0x86, 0x26, 0xed, 0x79, 0xd4, 0x51, 0x14, 0x08, 0x00, 0xe0, 0x3b, 0x59, 0xb9, 0x56, 0xf8, 0x21, 0x0e, 0x55, 0x60, 0x67, 0x40, 0x7d, 0x13, 0xdc, + 0x90, 0xfa, 0x9e, 0x8b, 0x87, 0x2b, 0xfb, 0x8f, 0xa0, 0x82, 0x06, 0x65, 0x03, 0x82, 0x06, 0x61, 0x00, 0xda, 0x18, 0x71, 0x2d, 0x31, 0x6e, 0x98, 0xdc, 0x7a, 0xc8, 0xc3, 0xca, 0x47, 0x37, 0x0e, + 0xbd, 0x77, 0x0c, 0xe3, 0x2b, 0x3b, 0xd4, 0xb1, 0xa0, 0xc9, 0x52, 0x9a, 0xc6, 0xec, 0x8e, 0xe0, 0x28, 0xb1, 0xcd, 0xb2, 0x65, 0x1c, 0xb5, 0xa6, 0xbb, 0x3c, 0x0c, 0x6d, 0xf1, 0x24, 0x0a, 0x3b, + 0x91, 0x4b, 0x56, 0x56, 0xc0, 0xdc, 0x51, 0xc2, 0xb9, 0x1b, 0xfc, 0xbc, 0x37, 0xa4, 0x66, 0x02, 0x87, 0xd4, 0x4f, 0x81, 0xf8, 0x53, 0xc7, 0xf4, 0x9a, 0x6d, 0x06, 0x03, 0xd6, 0xd7, 0x23, 0xcb, + 0xec, 0x01, 0x5f, 0xbc, 0x43, 0x4a, 0x38, 0x24, 0x1c, 0x10, 0x9c, 0x7e, 0xd5, 0xb1, 0xcc, 0x46, 0x1a, 0x2c, 0xcb, 0x9a, 0xb7, 0x14, 0x0f, 0x19, 0xf3, 0x7a, 0x13, 0xbb, 0x70, 0x1e, 0x14, 0x2b, + 0xd5, 0x4b, 0x64, 0xec, 0x6b, 0x76, 0xfe, 0xc3, 0x3b, 0x69, 0xc2, 0x91, 0x8c, 0xb0, 0x17, 0xc4, 0x14, 0x34, 0x23, 0x00, 0x9a, 0x3c, 0x07, 0xb5, 0xc1, 0x81, 0xb0, 0xc1, 0xeb, 0x49, 0x4a, 0x62, + 0xab, 0xc8, 0x39, 0x13, 0x97, 0x08, 0x9e, 0xa6, 0x64, 0x09, 0x67, 0xc1, 0x20, 0x49, 0x84, 0xcd, 0x48, 0x4c, 0xcc, 0xb0, 0x0a, 0x9a, 0x17, 0xd0, 0x87, 0x21, 0x84, 0x28, 0xef, 0x3b, 0xb7, 0x08, + 0x78, 0x3e, 0x12, 0x82, 0x71, 0x04, 0x41, 0x73, 0x75, 0xb6, 0x95, 0x6f, 0xb5, 0x00, 0x53, 0xd0, 0x48, 0xa4, 0x79, 0x14, 0x95, 0x82, 0x4a, 0x34, 0x80, 0xa5, 0xb7, 0x83, 0x02, 0x56, 0x09, 0x6f, + 0xdd, 0x72, 0x5c, 0x30, 0x8b, 0x3b, 0xe8, 0x4a, 0x07, 0xf3, 0x63, 0x2e, 0x24, 0x95, 0xc6, 0x2e, 0x96, 0x39, 0x9d, 0x80, 0xbf, 0xa7, 0x45, 0xb9, 0x84, 0x1a, 0x18, 0x33, 0xbc, 0x1d, 0x27, 0xba, + 0x45, 0xa5, 0x21, 0x68, 0xee, 0x59, 0x00, 0x6c, 0x3a, 0x3a, 0x8c, 0x4a, 0x5a, 0x4f, 0x50, 0x88, 0xfc, 0x73, 0x71, 0x81, 0xab, 0x51, 0x96, 0xf7, 0xb1, 0xb4, 0x9a, 0x2e, 0xd8, 0x13, 0x13, 0x4e, + 0x11, 0x2f, 0x73, 0x0b, 0x99, 0x1c, 0x54, 0xa7, 0x19, 0x6b, 0xcf, 0x5f, 0xc7, 0x6e, 0x13, 0x4c, 0x58, 0x43, 0xe1, 0x69, 0x88, 0x51, 0xb2, 0xf8, 0x69, 0xaf, 0xaf, 0xb0, 0x27, 0x87, 0xd9, 0xc2, + 0xf1, 0x36, 0x90, 0x2d, 0xc7, 0xa7, 0xf3, 0xd6, 0x21, 0x56, 0xd1, 0x5e, 0xc3, 0x09, 0x56, 0x40, 0x92, 0xc6, 0x1d, 0x83, 0xb0, 0x98, 0x6c, 0x48, 0x40, 0x99, 0x81, 0xf3, 0xc1, 0x86, 0x88, 0x0a, + 0x2f, 0x63, 0xd5, 0x86, 0x0a, 0xb6, 0x01, 0xde, 0xac, 0x2b, 0x6b, 0xa1, 0xb4, 0x28, 0x17, 0x9d, 0x73, 0x53, 0x3e, 0xb7, 0xa3, 0xa5, 0x11, 0x3b, 0x85, 0x61, 0xf1, 0x0b, 0x45, 0xc3, 0xcd, 0xe2, + 0x82, 0xb6, 0xea, 0xd6, 0xab, 0x6c, 0x60, 0x4f, 0x09, 0xc1, 0x7b, 0xfd, 0xa0, 0x83, 0x13, 0xa3, 0x26, 0x07, 0x67, 0x5a, 0xdf, 0x64, 0x31, 0xca, 0x87, 0x18, 0xe9, 0xc4, 0x3a, 0x73, 0x73, 0x32, + 0x27, 0xe7, 0x3b, 0xc6, 0x1a, 0xc8, 0x45, 0xba, 0x90, 0x77, 0x55, 0xce, 0xc6, 0x89, 0x25, 0xe5, 0xe2, 0xbf, 0xe9, 0x12, 0x95, 0x9d, 0xb8, 0x6f, 0xbf, 0xe2, 0x15, 0x6f, 0xd5, 0xbb, 0xdb, 0xf0, + 0xc9, 0xdf, 0x8b, 0x53, 0x02, 0xaa, 0x8d, 0x90, 0xa2, 0x2d, 0x12, 0x27, 0x0e, 0x00, 0x65, 0x51, 0xe4, 0x76, 0x7e, 0x45, 0x26, 0x8e, 0xd9, 0x69, 0x26, 0x54, 0x44, 0x78, 0x11, 0xea, 0xb8, 0x4f, + 0x04, 0x99, 0xa8, 0xa5, 0x8c, 0xf7, 0xc0, 0x4a, 0x59, 0x56, 0x98, 0x52, 0x80, 0x45, 0xf2, 0x98, 0x97, 0xc8, 0xfa, 0x96, 0xd0, 0x6c, 0xce, 0x51, 0xe6, 0xaf, 0xea, 0xc4, 0x33, 0x95, 0x89, 0xc9, + 0x41, 0xc8, 0x55, 0x63, 0xd7, 0x0f, 0xac, 0xe1, 0x92, 0x88, 0x94, 0xba, 0xc0, 0x36, 0x19, 0xdf, 0xf4, 0xbe, 0x3f, 0x43, 0x14, 0xa3, 0xf7, 0x35, 0x1a, 0x09, 0xa4, 0x86, 0xb5, 0x04, 0x1e, 0x7c, + 0xb2, 0xda, 0x8b, 0x96, 0xbc, 0x66, 0x26, 0xa4, 0x93, 0x17, 0x35, 0x7c, 0x41, 0x52, 0xa5, 0x1b, 0xa3, 0xc2, 0x8c, 0x7e, 0x0c, 0x9d, 0xb4, 0x1a, 0x06, 0xa2, 0x82, 0x90, 0xf2, 0x18, 0x73, 0x11, + 0x07, 0xc9, 0x54, 0xd8, 0xa6, 0x6f, 0x80, 0x1d, 0x7d, 0xe1, 0x2a, 0x03, 0x71, 0x16, 0x99, 0x0b, 0x6c, 0x53, 0xc1, 0x29, 0xf1, 0x85, 0xc3, 0x45, 0xf2, 0x7e, 0x51, 0x8b, 0x2d, 0x5a, 0x91, 0x25, + 0xa0, 0x70, 0x76, 0xd9, 0x91, 0xb7, 0xda, 0xc7, 0xcc, 0x65, 0xa8, 0x56, 0x2e, 0xfb, 0xcc, 0x32, 0xa9, 0xca, 0x4a, 0xd9, 0x02, 0x63, 0xb0, 0x4a, 0x4f, 0x90, 0x36, 0x11, 0x6c, 0x7b, 0x97, 0x48, + 0x04, 0x96, 0x31, 0x75, 0x75, 0x65, 0x0d, 0xcc, 0x21, 0x52, 0xb5, 0xbc, 0x0e, 0x74, 0x40, 0x7e, 0x12, 0xfa, 0x8e, 0x4f, 0xfc, 0xcc, 0xff, 0x76, 0xc0, 0x1a, 0x97, 0x4b, 0xd6, 0x11, 0x02, 0xe1, + 0xf5, 0x29, 0x64, 0x96, 0xc7, 0x1d, 0x07, 0x64, 0xe1, 0x32, 0x29, 0xff, 0xe7, 0x84, 0x6f, 0x33, 0x6e, 0x34, 0xca, 0xc9, 0x04, 0xca, 0x56, 0x70, 0xf8, 0xcd, 0x50, 0x52, 0x42, 0x7a, 0x79, 0xc0, + 0x91, 0xa9, 0x71, 0x21, 0x0c, 0x5c, 0xff, 0x66, 0x7a, 0xac, 0x24, 0x93, 0x66, 0xe1, 0x0d, 0x2b, 0x11, 0x37, 0x6c, 0xa3, 0x9d, 0x93, 0x52, 0x04, 0xb1, 0x2c, 0xc5, 0x85, 0xe9, 0x40, 0x54, 0x03, + 0x62, 0x5f, 0xb3, 0x2c, 0xb5, 0xe5, 0xc3, 0x1b, 0x62, 0x34, 0x81, 0x60, 0x51, 0x5c, 0xcc, 0x4f, 0xda, 0xf5, 0x70, 0x2d, 0x6b, 0xab, 0x5c, 0x37, 0x3d, 0xb6, 0xf3, 0x50, 0xd3, 0xe6, 0x3a, 0x5c, + 0xe3, 0xca, 0x54, 0x74, 0xa0, 0xcf, 0x15, 0x67, 0x04, 0x2c, 0xa3, 0x25, 0x89, 0x86, 0xff, 0x75, 0xbd, 0xfc, 0xd9, 0x29, 0xe6, 0x46, 0x2f, 0x36, 0xbc, 0xcc, 0x3f, 0x5a, 0x93, 0x35, 0x2a, 0x2b, + 0x36, 0xcb, 0x16, 0x2e, 0x18, 0x74, 0xc7, 0x42, 0x87, 0x0a, 0x97, 0xb1, 0x67, 0xa0, 0x50, 0x37, 0x36, 0x24, 0xea, 0xeb, 0x7e, 0x50, 0x73, 0x25, 0x6b, 0x72, 0x11, 0xb2, 0xd9, 0x4b, 0x84, 0x06, + 0xcd, 0x6c, 0x95, 0x33, 0xb1, 0x53, 0x64, 0x08, 0xab, 0x0a, 0x29, 0xe5, 0xb2, 0xf0, 0xc9, 0x54, 0xec, 0xe0, 0x0f, 0xbb, 0xeb, 0x17, 0x6d, 0x72, 0x4d, 0x4c, 0xf4, 0x43, 0xcf, 0x70, 0x20, 0xd5, + 0xfa, 0x70, 0x94, 0xcc, 0x1b, 0x1b, 0xe6, 0x97, 0xba, 0xd3, 0x36, 0x74, 0xe4, 0x09, 0x9e, 0xc7, 0xbb, 0x18, 0xf4, 0x57, 0x71, 0x28, 0xcd, 0xd9, 0x7c, 0xcd, 0x6d, 0x44, 0x62, 0xe5, 0x60, 0x7c, + 0x51, 0x2a, 0x3e, 0x36, 0x24, 0x8e, 0x3d, 0xda, 0xa2, 0xec, 0x08, 0x9a, 0xef, 0xc4, 0xce, 0x48, 0x5c, 0x49, 0xd7, 0xb0, 0x09, 0xc8, 0xd6, 0x31, 0x15, 0xfc, 0x81, 0xff, 0x3a, 0x62, 0xd1, 0x5a, + 0x88, 0x44, 0x1c, 0x03, 0xea, 0x1c, 0x2e, 0x72, 0xc4, 0x88, 0x39, 0xfc, 0x6a, 0xd7, 0x3a, 0x30, 0x74, 0x4a, 0x62, 0xb7, 0xb2, 0x16, 0x45, 0xa6, 0xaf, 0x7d, 0x61, 0xb6, 0x38, 0x3b, 0x22, 0x1e, + 0x21, 0x90, 0x55, 0x57, 0xcd, 0x29, 0xd9, 0x24, 0xa6, 0x09, 0x86, 0xc5, 0x11, 0xc1, 0xeb, 0xbc, 0x31, 0x6d, 0x56, 0x30, 0xa2, 0x41, 0x43, 0x23, 0xf5, 0x3a, 0xd5, 0x59, 0x94, 0xf6, 0xb3, 0x65, + 0x39, 0xf9, 0xc4, 0x40, 0x75, 0xa5, 0x33, 0xe4, 0x81, 0xc0, 0x84, 0x45, 0xd9, 0xca, 0x9e, 0x9d, 0x38, 0x21, 0x19, 0x38, 0x8b, 0xd1, 0xd7, 0x50, 0x52, 0x21, 0x7a, 0x94, 0x4c, 0xcc, 0x7b, 0xe9, + 0x09, 0xe2, 0x19, 0x71, 0x1f, 0xcc, 0x79, 0x24, 0x76, 0x92, 0x13, 0xa1, 0x92, 0x53, 0x4a, 0x55, 0x80, 0x08, 0x15, 0x7a, 0x39, 0x6e, 0xdf, 0xf4, 0x80, 0xcc, 0x3b, 0x52, 0x0f, 0xf8, 0x18, 0xb3, + 0x8b, 0x13, 0x5c, 0x18, 0xa8, 0x0d, 0x51, 0x05, 0xe6, 0x78, 0x83, 0x6c, 0x39, 0x5c, 0x28, 0xe9, 0x2f, 0x7a, 0x3c, 0x4e, 0x93, 0xc0, 0x10, 0x35, 0xf3, 0x41, 0x11, 0xcc, 0x49, 0x02, 0xd0, 0xc0, + 0x33, 0xa6, 0x3f, 0x23, 0x6a, 0x71, 0xda, 0x97, 0x4a, 0x6f, 0x40, 0x4f, 0x7a, 0xa7, 0xb5, 0xe5, 0x82, 0xc7, 0x58, 0x14, 0x2f, 0xc1, 0x82, 0x6b, 0xba, 0x98, 0xb2, 0x7d, 0x57, 0xc2, 0xe2, 0x10, + 0x3e, 0x10, 0xe3, 0x0d, 0x32, 0x79, 0x7b, 0x96, 0x77, 0x14, 0xd1, 0x56, 0x61, 0x11, 0x13, 0x71, 0xa2, 0xd9, 0xc5, 0x39, 0x98, 0x12, 0x46, 0x46, 0x22, 0x63, 0x5b, 0x44, 0x21, 0x26, 0xb0, 0x98, + 0x36, 0xb0, 0x81, 0x82, 0x72, 0x47, 0xd0, 0x54, 0x22, 0x97, 0x2b, 0xd0, 0x32, 0x0d, 0x8f, 0x42, 0xbf, 0x57, 0xe3, 0x49, 0x46, 0x12, 0x34, 0xe4, 0xd9, 0x4f, 0x01, 0x18, 0x50, 0xba, 0xb5, 0xc0, + 0x49, 0xb6, 0x2a, 0x59, 0x43, 0x38, 0x66, 0xfc, 0xce, 0x69, 0x66, 0x49, 0x5c, 0x26, 0x5c, 0x47, 0x65, 0xa5, 0x6c, 0x06, 0xb9, 0xfc, 0x42, 0x76, 0x54, 0x87, 0x85, 0xf4, 0x68, 0x28, 0xca, 0x60, + 0x2d, 0xc6, 0xd0, 0x54, 0x1f, 0x25, 0x07, 0x89, 0xc4, 0x9e, 0x8b, 0x06, 0x55, 0x9c, 0x43, 0x44, 0x60, 0xa8, 0x43, 0x80, 0x98, 0x54, 0xe5, 0xb4, 0x6e, 0x89, 0x38, 0x9f, 0x10, 0xf4, 0x89, 0x66, + 0x74, 0x91, 0xc1, 0x93, 0x5e, 0x8a, 0xfb, 0x9e, 0xb4, 0x71, 0x8f, 0x86, 0xac, 0x45, 0x89, 0x32, 0xbc, 0xf3, 0x3c, 0x9a, 0xbe, 0xcb, 0x2d, 0xc0, 0xc0, 0x93, 0xa7, 0xe8, 0x1d, 0xa0, 0x32, 0x7b, + 0xb6, 0x37, 0x52, 0x81, 0x05, 0xc3, 0x58, 0xeb, 0x76, 0x8d, 0x32, 0x3a, 0x37, 0xd4, 0x0a, 0x8c, 0x19, 0x9b, 0x7c, 0x4b, 0xb1, 0xd7, 0x2b, 0x72, 0xb6, 0x90, 0xb3, 0x6d, 0xd2, 0x7a, 0x93, 0x55, + 0x19, 0x1b, 0x3c, 0x3a, 0xa6, 0x75, 0xa7, 0xe6, 0xf8, 0x55, 0xeb, 0x50, 0x5f, 0x57, 0x98, 0x65, 0xdb, 0xd8, 0x91, 0x05, 0x65, 0x50, 0x5e, 0x7c, 0x0f, 0xdd, 0x54, 0x5c, 0xbb, 0xb8, 0x71, 0xb0, + 0xb2, 0xcc, 0x01, 0x25, 0xb7, 0x4f, 0x6b, 0x0c, 0x9b, 0x79, 0x67, 0x0a, 0x62, 0x02, 0xd1, 0xb9, 0x15, 0x4a, 0xc7, 0x76, 0x6b, 0x19, 0x19, 0xc4, 0x89, 0x58, 0x90, 0x86, 0xad, 0x8b, 0x45, 0xbe, + 0x0d, 0x79, 0xc9, 0x76, 0xc3, 0xc3, 0x9d, 0x6b, 0x25, 0x21, 0x3b, 0xb0, 0xb7, 0x8a, 0x57, 0x50, 0xe6, 0xa8, 0xeb, 0x34, 0x33, 0x0b, 0xb3, 0xcf, 0xf2, 0xb1, 0xc0, 0x72, 0x2a, 0xc8, 0x83, 0xb0, + 0x48, 0xf4, 0xb8, 0xcd, 0x06, 0x19, 0x6d, 0xa8, 0xaa, 0x8b, 0x05, 0xda, 0x42, 0x67, 0x55, 0x2b, 0xf8, 0x7a, 0xbc, 0xa5, 0x12, 0x4d, 0xc3, 0x58, 0xa8, 0x38, 0x10, 0x40, 0xe9, 0xb8, 0x1f, 0xb0, + 0x84, 0x43, 0x15, 0x02, 0x15, 0xd6, 0x92, 0x23, 0x28, 0x00, 0x0a, 0xc0, 0xb7, 0x88, 0xb1, 0x21, 0x93, 0x1a, 0x26, 0x7d, 0x80, 0x61, 0x9c, 0xe7, 0xd2, 0x9c, 0xd7, 0x6b, 0x60, 0xcf, 0x65, 0x83, + 0xdc, 0xe8, 0xce, 0xbc, 0x49, 0x01, 0x85, 0x73, 0x6c, 0x81, 0x8b, 0x25, 0xad, 0x26, 0x0b, 0x66, 0x7b, 0x1f, 0xfd, 0x46, 0x20, 0x6d, 0x01, 0x04, 0x55, 0x3a, 0xa9, 0xfb, 0x30, 0x45, 0x54, 0xa2, + 0x1c, 0x32, 0x72, 0x44, 0xce, 0x78, 0xaf, 0xdb, 0xd3, 0xb4, 0x62, 0x36, 0x1b, 0xb0, 0x68, 0xa1, 0x55, 0x63, 0x64, 0x09, 0xf5, 0x74, 0xc5, 0x71, 0x65, 0x72, 0xe2, 0xa5, 0xf2, 0xa4, 0xb0, 0x4f, + 0xb8, 0xaa, 0xd1, 0x23, 0x66, 0x84, 0x84, 0x17, 0x87, 0x56, 0x2a, 0xaf, 0x46, 0xc2, 0xc0, 0xda, 0x46, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, + 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, 0x54, 0xa3, 0x16, 0x65, 0x29, 0xb5, 0x39, 0x22, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + }, + .spki_len = 1603, + .spki = { + 0x30, 0x82, 0x06, 0x3f, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x05, 0x04, 0x04, 0x05, 0x00, 0x03, 0x82, 0x06, 0x2a, 0x00, 0x30, 0x82, 0x06, 0x25, 0x03, 0x82, + 0x06, 0x21, 0x00, 0xda, 0x18, 0x71, 0x2d, 0x31, 0x6e, 0x98, 0xdc, 0x7a, 0xc8, 0xc3, 0xca, 0x47, 0x37, 0x0e, 0xbd, 0x77, 0x0c, 0xe3, 0x2b, 0x3b, 0xd4, 0xb1, 0xa0, 0xc9, 0x52, 0x9a, 0xc6, 0xec, + 0x8e, 0xe0, 0x28, 0xb1, 0xcd, 0xb2, 0x65, 0x1c, 0xb5, 0xa6, 0xbb, 0x3c, 0x0c, 0x6d, 0xf1, 0x24, 0x0a, 0x3b, 0x91, 0x4b, 0x56, 0x56, 0xc0, 0xdc, 0x51, 0xc2, 0xb9, 0x1b, 0xfc, 0xbc, 0x37, 0xa4, + 0x66, 0x02, 0x87, 0xd4, 0x4f, 0x81, 0xf8, 0x53, 0xc7, 0xf4, 0x9a, 0x6d, 0x06, 0x03, 0xd6, 0xd7, 0x23, 0xcb, 0xec, 0x01, 0x5f, 0xbc, 0x43, 0x4a, 0x38, 0x24, 0x1c, 0x10, 0x9c, 0x7e, 0xd5, 0xb1, + 0xcc, 0x46, 0x1a, 0x2c, 0xcb, 0x9a, 0xb7, 0x14, 0x0f, 0x19, 0xf3, 0x7a, 0x13, 0xbb, 0x70, 0x1e, 0x14, 0x2b, 0xd5, 0x4b, 0x64, 0xec, 0x6b, 0x76, 0xfe, 0xc3, 0x3b, 0x69, 0xc2, 0x91, 0x8c, 0xb0, + 0x17, 0xc4, 0x14, 0x34, 0x23, 0x00, 0x9a, 0x3c, 0x07, 0xb5, 0xc1, 0x81, 0xb0, 0xc1, 0xeb, 0x49, 0x4a, 0x62, 0xab, 0xc8, 0x39, 0x13, 0x97, 0x08, 0x9e, 0xa6, 0x64, 0x09, 0x67, 0xc1, 0x20, 0x49, + 0x84, 0xcd, 0x48, 0x4c, 0xcc, 0xb0, 0x0a, 0x9a, 0x17, 0xd0, 0x87, 0x21, 0x84, 0x28, 0xef, 0x3b, 0xb7, 0x08, 0x78, 0x3e, 0x12, 0x82, 0x71, 0x04, 0x41, 0x73, 0x75, 0xb6, 0x95, 0x6f, 0xb5, 0x00, + 0x53, 0xd0, 0x48, 0xa4, 0x79, 0x14, 0x95, 0x82, 0x4a, 0x34, 0x80, 0xa5, 0xb7, 0x83, 0x02, 0x56, 0x09, 0x6f, 0xdd, 0x72, 0x5c, 0x30, 0x8b, 0x3b, 0xe8, 0x4a, 0x07, 0xf3, 0x63, 0x2e, 0x24, 0x95, + 0xc6, 0x2e, 0x96, 0x39, 0x9d, 0x80, 0xbf, 0xa7, 0x45, 0xb9, 0x84, 0x1a, 0x18, 0x33, 0xbc, 0x1d, 0x27, 0xba, 0x45, 0xa5, 0x21, 0x68, 0xee, 0x59, 0x00, 0x6c, 0x3a, 0x3a, 0x8c, 0x4a, 0x5a, 0x4f, + 0x50, 0x88, 0xfc, 0x73, 0x71, 0x81, 0xab, 0x51, 0x96, 0xf7, 0xb1, 0xb4, 0x9a, 0x2e, 0xd8, 0x13, 0x13, 0x4e, 0x11, 0x2f, 0x73, 0x0b, 0x99, 0x1c, 0x54, 0xa7, 0x19, 0x6b, 0xcf, 0x5f, 0xc7, 0x6e, + 0x13, 0x4c, 0x58, 0x43, 0xe1, 0x69, 0x88, 0x51, 0xb2, 0xf8, 0x69, 0xaf, 0xaf, 0xb0, 0x27, 0x87, 0xd9, 0xc2, 0xf1, 0x36, 0x90, 0x2d, 0xc7, 0xa7, 0xf3, 0xd6, 0x21, 0x56, 0xd1, 0x5e, 0xc3, 0x09, + 0x56, 0x40, 0x92, 0xc6, 0x1d, 0x83, 0xb0, 0x98, 0x6c, 0x48, 0x40, 0x99, 0x81, 0xf3, 0xc1, 0x86, 0x88, 0x0a, 0x2f, 0x63, 0xd5, 0x86, 0x0a, 0xb6, 0x01, 0xde, 0xac, 0x2b, 0x6b, 0xa1, 0xb4, 0x28, + 0x17, 0x9d, 0x73, 0x53, 0x3e, 0xb7, 0xa3, 0xa5, 0x11, 0x3b, 0x85, 0x61, 0xf1, 0x0b, 0x45, 0xc3, 0xcd, 0xe2, 0x82, 0xb6, 0xea, 0xd6, 0xab, 0x6c, 0x60, 0x4f, 0x09, 0xc1, 0x7b, 0xfd, 0xa0, 0x83, + 0x13, 0xa3, 0x26, 0x07, 0x67, 0x5a, 0xdf, 0x64, 0x31, 0xca, 0x87, 0x18, 0xe9, 0xc4, 0x3a, 0x73, 0x73, 0x32, 0x27, 0xe7, 0x3b, 0xc6, 0x1a, 0xc8, 0x45, 0xba, 0x90, 0x77, 0x55, 0xce, 0xc6, 0x89, + 0x25, 0xe5, 0xe2, 0xbf, 0xe9, 0x12, 0x95, 0x9d, 0xb8, 0x6f, 0xbf, 0xe2, 0x15, 0x6f, 0xd5, 0xbb, 0xdb, 0xf0, 0xc9, 0xdf, 0x8b, 0x53, 0x02, 0xaa, 0x8d, 0x90, 0xa2, 0x2d, 0x12, 0x27, 0x0e, 0x00, + 0x65, 0x51, 0xe4, 0x76, 0x7e, 0x45, 0x26, 0x8e, 0xd9, 0x69, 0x26, 0x54, 0x44, 0x78, 0x11, 0xea, 0xb8, 0x4f, 0x04, 0x99, 0xa8, 0xa5, 0x8c, 0xf7, 0xc0, 0x4a, 0x59, 0x56, 0x98, 0x52, 0x80, 0x45, + 0xf2, 0x98, 0x97, 0xc8, 0xfa, 0x96, 0xd0, 0x6c, 0xce, 0x51, 0xe6, 0xaf, 0xea, 0xc4, 0x33, 0x95, 0x89, 0xc9, 0x41, 0xc8, 0x55, 0x63, 0xd7, 0x0f, 0xac, 0xe1, 0x92, 0x88, 0x94, 0xba, 0xc0, 0x36, + 0x19, 0xdf, 0xf4, 0xbe, 0x3f, 0x43, 0x14, 0xa3, 0xf7, 0x35, 0x1a, 0x09, 0xa4, 0x86, 0xb5, 0x04, 0x1e, 0x7c, 0xb2, 0xda, 0x8b, 0x96, 0xbc, 0x66, 0x26, 0xa4, 0x93, 0x17, 0x35, 0x7c, 0x41, 0x52, + 0xa5, 0x1b, 0xa3, 0xc2, 0x8c, 0x7e, 0x0c, 0x9d, 0xb4, 0x1a, 0x06, 0xa2, 0x82, 0x90, 0xf2, 0x18, 0x73, 0x11, 0x07, 0xc9, 0x54, 0xd8, 0xa6, 0x6f, 0x80, 0x1d, 0x7d, 0xe1, 0x2a, 0x03, 0x71, 0x16, + 0x99, 0x0b, 0x6c, 0x53, 0xc1, 0x29, 0xf1, 0x85, 0xc3, 0x45, 0xf2, 0x7e, 0x51, 0x8b, 0x2d, 0x5a, 0x91, 0x25, 0xa0, 0x70, 0x76, 0xd9, 0x91, 0xb7, 0xda, 0xc7, 0xcc, 0x65, 0xa8, 0x56, 0x2e, 0xfb, + 0xcc, 0x32, 0xa9, 0xca, 0x4a, 0xd9, 0x02, 0x63, 0xb0, 0x4a, 0x4f, 0x90, 0x36, 0x11, 0x6c, 0x7b, 0x97, 0x48, 0x04, 0x96, 0x31, 0x75, 0x75, 0x65, 0x0d, 0xcc, 0x21, 0x52, 0xb5, 0xbc, 0x0e, 0x74, + 0x40, 0x7e, 0x12, 0xfa, 0x8e, 0x4f, 0xfc, 0xcc, 0xff, 0x76, 0xc0, 0x1a, 0x97, 0x4b, 0xd6, 0x11, 0x02, 0xe1, 0xf5, 0x29, 0x64, 0x96, 0xc7, 0x1d, 0x07, 0x64, 0xe1, 0x32, 0x29, 0xff, 0xe7, 0x84, + 0x6f, 0x33, 0x6e, 0x34, 0xca, 0xc9, 0x04, 0xca, 0x56, 0x70, 0xf8, 0xcd, 0x50, 0x52, 0x42, 0x7a, 0x79, 0xc0, 0x91, 0xa9, 0x71, 0x21, 0x0c, 0x5c, 0xff, 0x66, 0x7a, 0xac, 0x24, 0x93, 0x66, 0xe1, + 0x0d, 0x2b, 0x11, 0x37, 0x6c, 0xa3, 0x9d, 0x93, 0x52, 0x04, 0xb1, 0x2c, 0xc5, 0x85, 0xe9, 0x40, 0x54, 0x03, 0x62, 0x5f, 0xb3, 0x2c, 0xb5, 0xe5, 0xc3, 0x1b, 0x62, 0x34, 0x81, 0x60, 0x51, 0x5c, + 0xcc, 0x4f, 0xda, 0xf5, 0x70, 0x2d, 0x6b, 0xab, 0x5c, 0x37, 0x3d, 0xb6, 0xf3, 0x50, 0xd3, 0xe6, 0x3a, 0x5c, 0xe3, 0xca, 0x54, 0x74, 0xa0, 0xcf, 0x15, 0x67, 0x04, 0x2c, 0xa3, 0x25, 0x89, 0x86, + 0xff, 0x75, 0xbd, 0xfc, 0xd9, 0x29, 0xe6, 0x46, 0x2f, 0x36, 0xbc, 0xcc, 0x3f, 0x5a, 0x93, 0x35, 0x2a, 0x2b, 0x36, 0xcb, 0x16, 0x2e, 0x18, 0x74, 0xc7, 0x42, 0x87, 0x0a, 0x97, 0xb1, 0x67, 0xa0, + 0x50, 0x37, 0x36, 0x24, 0xea, 0xeb, 0x7e, 0x50, 0x73, 0x25, 0x6b, 0x72, 0x11, 0xb2, 0xd9, 0x4b, 0x84, 0x06, 0xcd, 0x6c, 0x95, 0x33, 0xb1, 0x53, 0x64, 0x08, 0xab, 0x0a, 0x29, 0xe5, 0xb2, 0xf0, + 0xc9, 0x54, 0xec, 0xe0, 0x0f, 0xbb, 0xeb, 0x17, 0x6d, 0x72, 0x4d, 0x4c, 0xf4, 0x43, 0xcf, 0x70, 0x20, 0xd5, 0xfa, 0x70, 0x94, 0xcc, 0x1b, 0x1b, 0xe6, 0x97, 0xba, 0xd3, 0x36, 0x74, 0xe4, 0x09, + 0x9e, 0xc7, 0xbb, 0x18, 0xf4, 0x57, 0x71, 0x28, 0xcd, 0xd9, 0x7c, 0xcd, 0x6d, 0x44, 0x62, 0xe5, 0x60, 0x7c, 0x51, 0x2a, 0x3e, 0x36, 0x24, 0x8e, 0x3d, 0xda, 0xa2, 0xec, 0x08, 0x9a, 0xef, 0xc4, + 0xce, 0x48, 0x5c, 0x49, 0xd7, 0xb0, 0x09, 0xc8, 0xd6, 0x31, 0x15, 0xfc, 0x81, 0xff, 0x3a, 0x62, 0xd1, 0x5a, 0x88, 0x44, 0x1c, 0x03, 0xea, 0x1c, 0x2e, 0x72, 0xc4, 0x88, 0x39, 0xfc, 0x6a, 0xd7, + 0x3a, 0x30, 0x74, 0x4a, 0x62, 0xb7, 0xb2, 0x16, 0x45, 0xa6, 0xaf, 0x7d, 0x61, 0xb6, 0x38, 0x3b, 0x22, 0x1e, 0x21, 0x90, 0x55, 0x57, 0xcd, 0x29, 0xd9, 0x24, 0xa6, 0x09, 0x86, 0xc5, 0x11, 0xc1, + 0xeb, 0xbc, 0x31, 0x6d, 0x56, 0x30, 0xa2, 0x41, 0x43, 0x23, 0xf5, 0x3a, 0xd5, 0x59, 0x94, 0xf6, 0xb3, 0x65, 0x39, 0xf9, 0xc4, 0x40, 0x75, 0xa5, 0x33, 0xe4, 0x81, 0xc0, 0x84, 0x45, 0xd9, 0xca, + 0x9e, 0x9d, 0x38, 0x21, 0x19, 0x38, 0x8b, 0xd1, 0xd7, 0x50, 0x52, 0x21, 0x7a, 0x94, 0x4c, 0xcc, 0x7b, 0xe9, 0x09, 0xe2, 0x19, 0x71, 0x1f, 0xcc, 0x79, 0x24, 0x76, 0x92, 0x13, 0xa1, 0x92, 0x53, + 0x4a, 0x55, 0x80, 0x08, 0x15, 0x7a, 0x39, 0x6e, 0xdf, 0xf4, 0x80, 0xcc, 0x3b, 0x52, 0x0f, 0xf8, 0x18, 0xb3, 0x8b, 0x13, 0x5c, 0x18, 0xa8, 0x0d, 0x51, 0x05, 0xe6, 0x78, 0x83, 0x6c, 0x39, 0x5c, + 0x28, 0xe9, 0x2f, 0x7a, 0x3c, 0x4e, 0x93, 0xc0, 0x10, 0x35, 0xf3, 0x41, 0x11, 0xcc, 0x49, 0x02, 0xd0, 0xc0, 0x33, 0xa6, 0x3f, 0x23, 0x6a, 0x71, 0xda, 0x97, 0x4a, 0x6f, 0x40, 0x4f, 0x7a, 0xa7, + 0xb5, 0xe5, 0x82, 0xc7, 0x58, 0x14, 0x2f, 0xc1, 0x82, 0x6b, 0xba, 0x98, 0xb2, 0x7d, 0x57, 0xc2, 0xe2, 0x10, 0x3e, 0x10, 0xe3, 0x0d, 0x32, 0x79, 0x7b, 0x96, 0x77, 0x14, 0xd1, 0x56, 0x61, 0x11, + 0x13, 0x71, 0xa2, 0xd9, 0xc5, 0x39, 0x98, 0x12, 0x46, 0x46, 0x22, 0x63, 0x5b, 0x44, 0x21, 0x26, 0xb0, 0x98, 0x36, 0xb0, 0x81, 0x82, 0x72, 0x47, 0xd0, 0x54, 0x22, 0x97, 0x2b, 0xd0, 0x32, 0x0d, + 0x8f, 0x42, 0xbf, 0x57, 0xe3, 0x49, 0x46, 0x12, 0x34, 0xe4, 0xd9, 0x4f, 0x01, 0x18, 0x50, 0xba, 0xb5, 0xc0, 0x49, 0xb6, 0x2a, 0x59, 0x43, 0x38, 0x66, 0xfc, 0xce, 0x69, 0x66, 0x49, 0x5c, 0x26, + 0x5c, 0x47, 0x65, 0xa5, 0x6c, 0x06, 0xb9, 0xfc, 0x42, 0x76, 0x54, 0x87, 0x85, 0xf4, 0x68, 0x28, 0xca, 0x60, 0x2d, 0xc6, 0xd0, 0x54, 0x1f, 0x25, 0x07, 0x89, 0xc4, 0x9e, 0x8b, 0x06, 0x55, 0x9c, + 0x43, 0x44, 0x60, 0xa8, 0x43, 0x80, 0x98, 0x54, 0xe5, 0xb4, 0x6e, 0x89, 0x38, 0x9f, 0x10, 0xf4, 0x89, 0x66, 0x74, 0x91, 0xc1, 0x93, 0x5e, 0x8a, 0xfb, 0x9e, 0xb4, 0x71, 0x8f, 0x86, 0xac, 0x45, + 0x89, 0x32, 0xbc, 0xf3, 0x3c, 0x9a, 0xbe, 0xcb, 0x2d, 0xc0, 0xc0, 0x93, 0xa7, 0xe8, 0x1d, 0xa0, 0x32, 0x7b, 0xb6, 0x37, 0x52, 0x81, 0x05, 0xc3, 0x58, 0xeb, 0x76, 0x8d, 0x32, 0x3a, 0x37, 0xd4, + 0x0a, 0x8c, 0x19, 0x9b, 0x7c, 0x4b, 0xb1, 0xd7, 0x2b, 0x72, 0xb6, 0x90, 0xb3, 0x6d, 0xd2, 0x7a, 0x93, 0x55, 0x19, 0x1b, 0x3c, 0x3a, 0xa6, 0x75, 0xa7, 0xe6, 0xf8, 0x55, 0xeb, 0x50, 0x5f, 0x57, + 0x98, 0x65, 0xdb, 0xd8, 0x91, 0x05, 0x65, 0x50, 0x5e, 0x7c, 0x0f, 0xdd, 0x54, 0x5c, 0xbb, 0xb8, 0x71, 0xb0, 0xb2, 0xcc, 0x01, 0x25, 0xb7, 0x4f, 0x6b, 0x0c, 0x9b, 0x79, 0x67, 0x0a, 0x62, 0x02, + 0xd1, 0xb9, 0x15, 0x4a, 0xc7, 0x76, 0x6b, 0x19, 0x19, 0xc4, 0x89, 0x58, 0x90, 0x86, 0xad, 0x8b, 0x45, 0xbe, 0x0d, 0x79, 0xc9, 0x76, 0xc3, 0xc3, 0x9d, 0x6b, 0x25, 0x21, 0x3b, 0xb0, 0xb7, 0x8a, + 0x57, 0x50, 0xe6, 0xa8, 0xeb, 0x34, 0x33, 0x0b, 0xb3, 0xcf, 0xf2, 0xb1, 0xc0, 0x72, 0x2a, 0xc8, 0x83, 0xb0, 0x48, 0xf4, 0xb8, 0xcd, 0x06, 0x19, 0x6d, 0xa8, 0xaa, 0x8b, 0x05, 0xda, 0x42, 0x67, + 0x55, 0x2b, 0xf8, 0x7a, 0xbc, 0xa5, 0x12, 0x4d, 0xc3, 0x58, 0xa8, 0x38, 0x10, 0x40, 0xe9, 0xb8, 0x1f, 0xb0, 0x84, 0x43, 0x15, 0x02, 0x15, 0xd6, 0x92, 0x23, 0x28, 0x00, 0x0a, 0xc0, 0xb7, 0x88, + 0xb1, 0x21, 0x93, 0x1a, 0x26, 0x7d, 0x80, 0x61, 0x9c, 0xe7, 0xd2, 0x9c, 0xd7, 0x6b, 0x60, 0xcf, 0x65, 0x83, 0xdc, 0xe8, 0xce, 0xbc, 0x49, 0x01, 0x85, 0x73, 0x6c, 0x81, 0x8b, 0x25, 0xad, 0x26, + 0x0b, 0x66, 0x7b, 0x1f, 0xfd, 0x46, 0x20, 0x6d, 0x01, 0x04, 0x55, 0x3a, 0xa9, 0xfb, 0x30, 0x45, 0x54, 0xa2, 0x1c, 0x32, 0x72, 0x44, 0xce, 0x78, 0xaf, 0xdb, 0xd3, 0xb4, 0x62, 0x36, 0x1b, 0xb0, + 0x68, 0xa1, 0x55, 0x63, 0x64, 0x09, 0xf5, 0x74, 0xc5, 0x71, 0x65, 0x72, 0xe2, 0xa5, 0xf2, 0xa4, 0xb0, 0x4f, 0xb8, 0xaa, 0xd1, 0x23, 0x66, 0x84, 0x84, 0x17, 0x87, 0x56, 0x2a, 0xaf, 0x46, 0xc2, + 0xc0, 0xda, 0x46, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, 0x54, 0xa3, 0x16, 0x65, 0x29, + 0xb5, 0x39, 0x22, + }, + .secret_len = 32, + .secret = { + 0xfb, 0xc4, 0xee, 0xa6, 0x91, 0xee, 0xf4, 0xc1, 0xb4, 0x76, 0xa2, 0x99, 0x36, 0x45, 0x3f, 0x4c, 0x3d, 0x48, 0x81, 0x79, 0x4e, 0xe3, 0x7b, 0xaf, 0x0f, 0xd7, 0x28, 0x40, 0x74, 0x3e, 0x7b, 0x7d, + }, + .cipher_len = 1568, + .cipher = { + 0xc2, 0x7f, 0x01, 0x24, 0x4d, 0x4b, 0x3f, 0xb2, 0x1d, 0x84, 0x37, 0xf8, 0x40, 0x01, 0x7c, 0xcc, 0xb7, 0xb7, 0xda, 0xd5, 0xfb, 0x2b, 0x47, 0xb9, 0xb5, 0x7e, 0xae, 0x4f, 0x77, 0xd0, 0xa4, 0x55, + 0x5e, 0x50, 0x92, 0xa2, 0x49, 0x69, 0xf2, 0x27, 0x3e, 0x97, 0x02, 0x88, 0x4a, 0x08, 0x47, 0x7b, 0x56, 0x8d, 0x80, 0x17, 0xf1, 0x38, 0x75, 0xd1, 0xf5, 0xa6, 0xd4, 0x13, 0xbd, 0xd2, 0x28, 0xeb, + 0xb1, 0x12, 0x60, 0xf7, 0xf4, 0x52, 0x9c, 0xbc, 0xeb, 0xf9, 0xb6, 0x86, 0x2e, 0x8a, 0x84, 0x12, 0x35, 0xf2, 0x9f, 0x60, 0xf8, 0xe8, 0x41, 0x74, 0x34, 0x18, 0x9d, 0x57, 0x99, 0x20, 0xfe, 0x6b, + 0x98, 0xdb, 0xe7, 0x13, 0xec, 0x16, 0xc3, 0xfd, 0xdb, 0xb8, 0x1e, 0x73, 0x1d, 0x95, 0x6b, 0x06, 0xdb, 0x49, 0x80, 0xf4, 0x9c, 0x26, 0xf2, 0x86, 0x61, 0xff, 0x9c, 0xe6, 0xe9, 0xd8, 0x61, 0xec, + 0x7a, 0x09, 0x84, 0x0c, 0x19, 0xde, 0x0e, 0xb6, 0x72, 0x20, 0x71, 0xf8, 0xaa, 0x48, 0x36, 0x2d, 0x2f, 0xf1, 0x27, 0xa4, 0xae, 0x46, 0xf9, 0x93, 0x37, 0x82, 0x68, 0x32, 0xad, 0xac, 0x23, 0x91, + 0x65, 0xf2, 0x25, 0x85, 0xbb, 0x57, 0xa8, 0x89, 0xc9, 0xc6, 0xaf, 0x82, 0x36, 0x7e, 0xc7, 0xb0, 0x72, 0x37, 0xc0, 0x53, 0x5b, 0x31, 0xb3, 0x8c, 0x1c, 0xac, 0x40, 0xac, 0x1a, 0x0c, 0x95, 0x8a, + 0x18, 0x87, 0xfe, 0x34, 0x71, 0x10, 0x83, 0xfd, 0x37, 0xaf, 0x4b, 0xc5, 0xb1, 0xb4, 0xe1, 0xe2, 0xee, 0x28, 0x43, 0x69, 0x3d, 0x57, 0xdd, 0x1e, 0x65, 0x7d, 0x4c, 0x24, 0xed, 0x20, 0x7e, 0xe7, + 0x12, 0xad, 0x2a, 0x08, 0x91, 0x45, 0x81, 0x80, 0xe9, 0xe8, 0xbd, 0x36, 0xfc, 0x14, 0xd8, 0xd6, 0x33, 0xf5, 0xb7, 0x41, 0xce, 0xa1, 0x08, 0xd2, 0xd4, 0xfd, 0x75, 0x1c, 0x5a, 0x67, 0xb0, 0x5e, + 0x30, 0x32, 0x4a, 0x67, 0xe9, 0xdd, 0x75, 0xc9, 0x93, 0xd4, 0xfe, 0x08, 0x54, 0xfb, 0x78, 0xdf, 0x6f, 0x3d, 0x45, 0xa2, 0xa9, 0xc8, 0xe4, 0x25, 0x10, 0xf0, 0xc3, 0xd8, 0x02, 0x03, 0x71, 0x2f, + 0xb3, 0x9e, 0x36, 0xb5, 0xdd, 0x8b, 0x5c, 0xcd, 0x3d, 0x09, 0xce, 0xa9, 0x42, 0x03, 0xba, 0xf8, 0x72, 0x08, 0x45, 0x71, 0xec, 0xf9, 0x78, 0xbd, 0xb9, 0x54, 0x8a, 0x25, 0x0e, 0xe4, 0x90, 0x7b, + 0x4a, 0xfc, 0x31, 0xb2, 0x1f, 0x31, 0x9a, 0xe4, 0xbf, 0x0a, 0xb1, 0x9c, 0xbd, 0x11, 0xeb, 0xe1, 0x33, 0x59, 0xd1, 0xaa, 0xf4, 0xfd, 0xb8, 0x3b, 0x65, 0x02, 0x50, 0x14, 0x22, 0xa5, 0xfe, 0x50, + 0xa8, 0xa3, 0x8e, 0xf5, 0x3d, 0xeb, 0x60, 0x3c, 0xe2, 0x3f, 0xd9, 0x79, 0x2b, 0x04, 0xde, 0xb3, 0x78, 0x71, 0x9a, 0xb7, 0x69, 0xaa, 0x58, 0x97, 0xcc, 0x65, 0xe9, 0xb1, 0x63, 0x04, 0xce, 0xa5, + 0x37, 0xe1, 0x76, 0x2b, 0xd8, 0xc9, 0xb1, 0x09, 0xda, 0x14, 0xa8, 0x29, 0xe6, 0x41, 0x9f, 0x1b, 0x9f, 0xf8, 0xa4, 0x66, 0xe2, 0xa6, 0xd6, 0xb3, 0x4d, 0x74, 0xff, 0xe1, 0xa5, 0x92, 0x99, 0x18, + 0x17, 0x59, 0xd0, 0xd3, 0x87, 0xfc, 0xed, 0x1d, 0x90, 0x7f, 0x5f, 0xb5, 0xed, 0xb4, 0x26, 0xc0, 0x51, 0x30, 0xe6, 0xca, 0x59, 0x09, 0xb2, 0x76, 0xd1, 0xa4, 0x7e, 0x71, 0x3c, 0x30, 0xd9, 0x96, + 0xda, 0x5e, 0x8e, 0x57, 0xe7, 0x12, 0xc7, 0x77, 0x38, 0xf2, 0x1b, 0xe7, 0x4b, 0x42, 0xb5, 0x18, 0x43, 0x2d, 0xad, 0x7e, 0xf7, 0x3e, 0x6a, 0x8c, 0x43, 0xaa, 0x9a, 0x62, 0x69, 0x94, 0xd7, 0x1a, + 0x31, 0x81, 0x28, 0x51, 0x80, 0x6e, 0x9f, 0xbb, 0x1f, 0x2b, 0xd3, 0x56, 0xce, 0xa3, 0x9d, 0x95, 0xf2, 0xf8, 0x7c, 0xa3, 0x0d, 0xaf, 0x6f, 0x27, 0x33, 0xf7, 0xbc, 0xe7, 0x9f, 0x8d, 0xa9, 0x95, + 0x05, 0x1e, 0x49, 0xa7, 0xfd, 0x22, 0x64, 0x37, 0x9c, 0x0a, 0x75, 0x2e, 0x55, 0x3e, 0xd6, 0x08, 0xeb, 0x93, 0x44, 0xc7, 0x94, 0x98, 0xf6, 0x91, 0x53, 0x85, 0x64, 0xc5, 0x4f, 0x82, 0x3b, 0xb7, + 0x0b, 0x12, 0xb5, 0x9e, 0x88, 0x24, 0xb4, 0xa4, 0xbb, 0x1e, 0xea, 0xc6, 0x7c, 0x81, 0x0c, 0xcc, 0x2e, 0x23, 0x74, 0x47, 0x83, 0xce, 0x95, 0x80, 0x97, 0xf7, 0xa6, 0xbc, 0x6e, 0x1f, 0x17, 0x59, + 0x75, 0x21, 0xb8, 0xc3, 0xd1, 0xee, 0x85, 0x96, 0xa2, 0x9f, 0xfe, 0xf1, 0x4e, 0xd9, 0x16, 0x32, 0x09, 0x7c, 0x16, 0xd5, 0x06, 0x5d, 0xb2, 0xa9, 0x63, 0xca, 0x73, 0x83, 0xac, 0x60, 0xad, 0x8f, + 0x4e, 0xd0, 0xd4, 0x1b, 0xd0, 0xbc, 0x3b, 0xaf, 0x19, 0x8c, 0x51, 0x25, 0xae, 0x91, 0x15, 0x06, 0xc9, 0x26, 0xd4, 0xc1, 0x17, 0x85, 0xfd, 0x61, 0x82, 0x29, 0xbf, 0xf5, 0x4c, 0xb1, 0x16, 0x1a, + 0xb8, 0xfc, 0x7b, 0x51, 0xda, 0xec, 0xcc, 0xd9, 0x13, 0x1e, 0xdf, 0x43, 0x7d, 0x8e, 0x52, 0x8e, 0x75, 0x81, 0xb8, 0x2c, 0x66, 0x0e, 0x8c, 0x5e, 0x25, 0x12, 0xd5, 0xf6, 0x38, 0x0a, 0x52, 0x8f, + 0x2a, 0xe4, 0xae, 0xe2, 0x63, 0xdb, 0x96, 0x76, 0x02, 0x4b, 0xc7, 0xad, 0x39, 0x8b, 0xc9, 0xcd, 0xda, 0xd6, 0x07, 0x96, 0x8b, 0xba, 0xb2, 0x23, 0x29, 0xe0, 0x4d, 0x6e, 0x77, 0x1f, 0xe6, 0x47, + 0x10, 0x7a, 0xc4, 0x66, 0x67, 0xa5, 0x1a, 0xd5, 0x58, 0xa6, 0x35, 0xf0, 0x26, 0x95, 0x1f, 0x4f, 0x48, 0xc8, 0x88, 0xd7, 0x01, 0xc2, 0xaf, 0xf4, 0xea, 0xb4, 0xe3, 0x4a, 0xdb, 0x15, 0x9a, 0xbb, + 0xbf, 0xab, 0xe5, 0x9b, 0x3f, 0x4c, 0xf8, 0xaa, 0xb1, 0xdd, 0x66, 0x1e, 0x4d, 0xd0, 0xc5, 0x55, 0x8d, 0xc0, 0x59, 0x20, 0x2e, 0xe6, 0x46, 0x25, 0xa3, 0xb4, 0xb9, 0x2f, 0xf4, 0xd1, 0x56, 0x97, + 0xf1, 0x6c, 0x18, 0xd4, 0xd2, 0x33, 0x8c, 0xfb, 0x49, 0x6e, 0x07, 0x03, 0x52, 0x68, 0x71, 0xc9, 0x78, 0x4b, 0xac, 0x8e, 0xba, 0xe8, 0x27, 0x9c, 0xf2, 0x71, 0x3a, 0xf3, 0xcc, 0x2d, 0x44, 0x0e, + 0x8c, 0xd2, 0x00, 0x86, 0x7b, 0x85, 0x18, 0xaa, 0xd3, 0xb9, 0xe2, 0x85, 0x02, 0x7d, 0xa0, 0xad, 0xd9, 0xf0, 0x22, 0x9e, 0xd4, 0xe8, 0x42, 0xd0, 0x5e, 0x22, 0x6a, 0xda, 0xc1, 0x3a, 0x39, 0x52, + 0xe3, 0x83, 0x5c, 0x8f, 0xb0, 0xa4, 0x28, 0x74, 0xc9, 0x4c, 0x66, 0x1b, 0x39, 0xdf, 0x7b, 0x72, 0x88, 0x7d, 0x22, 0x7d, 0x58, 0x3c, 0xe6, 0xb3, 0xbd, 0x65, 0xf7, 0x95, 0x10, 0x7b, 0xd0, 0x93, + 0x38, 0x9b, 0xfe, 0xfd, 0x17, 0x68, 0xa5, 0x71, 0x6f, 0x68, 0x5b, 0x17, 0x4e, 0xd2, 0x3e, 0x94, 0xa5, 0x95, 0x6e, 0x29, 0xbb, 0x2d, 0xdb, 0x79, 0x21, 0x03, 0xe6, 0x2f, 0x68, 0x92, 0x8a, 0xcc, + 0x60, 0x3e, 0xec, 0x2f, 0xf5, 0x6d, 0xb1, 0x4c, 0x08, 0xb7, 0xcb, 0xe4, 0xe2, 0xb4, 0xf2, 0xe0, 0xea, 0xee, 0x54, 0x16, 0x2e, 0x95, 0xbb, 0x35, 0xef, 0x36, 0x30, 0x3e, 0xe3, 0xe6, 0xcc, 0x61, + 0x06, 0x13, 0x73, 0x87, 0x6f, 0x7a, 0x09, 0x6a, 0x8a, 0xf5, 0x7d, 0x78, 0x2f, 0x8c, 0x82, 0x03, 0xde, 0x93, 0x42, 0x3a, 0x37, 0x91, 0x22, 0xfe, 0x7d, 0xad, 0x77, 0x0c, 0x36, 0x90, 0xf9, 0x78, + 0x22, 0x84, 0x60, 0xd0, 0x25, 0xce, 0x93, 0xb1, 0xb3, 0x36, 0xc5, 0x73, 0xe4, 0xe5, 0x58, 0x40, 0xea, 0x65, 0xcf, 0xdd, 0x61, 0x22, 0xc6, 0x72, 0xc9, 0x12, 0xf5, 0x29, 0x39, 0xd9, 0xea, 0x5b, + 0xe0, 0x62, 0x10, 0xf5, 0xe7, 0xed, 0xb6, 0x5b, 0x66, 0x94, 0x5d, 0x70, 0x56, 0xf5, 0x59, 0xa7, 0xd6, 0x92, 0x53, 0xf4, 0xbd, 0xbc, 0x57, 0x9d, 0xe9, 0x64, 0xf3, 0xe9, 0x3a, 0x86, 0xfa, 0x38, + 0xb6, 0xa2, 0xc0, 0xb5, 0x43, 0x38, 0xdc, 0xe0, 0x93, 0xf0, 0xb4, 0x68, 0x4e, 0xe3, 0x61, 0x44, 0x9f, 0x16, 0xc2, 0x79, 0xa7, 0x2b, 0x77, 0x31, 0xe4, 0x46, 0x00, 0xa7, 0x02, 0x77, 0x68, 0xfd, + 0xd0, 0xf6, 0x43, 0xed, 0x10, 0x06, 0x4b, 0x98, 0xa9, 0xda, 0x03, 0x2f, 0x1f, 0x5d, 0xea, 0xd3, 0x11, 0xe1, 0x77, 0x33, 0x50, 0x94, 0xdb, 0x4e, 0x38, 0x51, 0x4e, 0xae, 0x15, 0xa8, 0xf8, 0xec, + 0xf2, 0xf2, 0x41, 0x4e, 0x37, 0x8e, 0xfb, 0xf9, 0x97, 0xb1, 0x06, 0x6b, 0x6f, 0x69, 0xd6, 0x69, 0x09, 0xa4, 0x7e, 0x29, 0x8a, 0x7f, 0xec, 0x96, 0x1a, 0x83, 0x78, 0x2e, 0x0e, 0x47, 0x0f, 0xe0, + 0x71, 0xde, 0xcf, 0x4b, 0x26, 0xac, 0xa6, 0xed, 0x68, 0x83, 0x59, 0xe1, 0x08, 0x50, 0x55, 0xfd, 0x2b, 0x5a, 0xe9, 0xf4, 0x91, 0x87, 0x49, 0x89, 0x7a, 0xf1, 0x33, 0x60, 0x60, 0x53, 0xd5, 0xf6, + 0xa8, 0x52, 0x8c, 0xcb, 0x31, 0xab, 0x7f, 0x3f, 0x2d, 0x89, 0xa9, 0x5c, 0x5f, 0x05, 0xb1, 0x57, 0x00, 0xe5, 0x32, 0xad, 0x81, 0xd5, 0x9d, 0x9d, 0xb8, 0xa2, 0xc2, 0x9c, 0xac, 0x93, 0x6e, 0x3f, + 0x33, 0xdf, 0xe2, 0x4b, 0x0b, 0x1b, 0x71, 0x90, 0x2d, 0xc9, 0xc3, 0x0e, 0xc8, 0xc7, 0x0b, 0xda, 0xba, 0x48, 0x4f, 0xcd, 0x2b, 0x94, 0x6d, 0x73, 0x5f, 0x16, 0xee, 0xad, 0x04, 0x03, 0x1c, 0xaf, + 0xde, 0x9e, 0xe0, 0x16, 0x96, 0xec, 0x9f, 0x0a, 0x8d, 0x5f, 0x36, 0xb6, 0x9c, 0x64, 0x2f, 0xfd, 0x0a, 0xd0, 0xd2, 0x54, 0x4f, 0x5e, 0x7f, 0xd8, 0x9a, 0x80, 0x49, 0x8e, 0xf6, 0x8e, 0x18, 0x16, + 0x17, 0xfa, 0xd4, 0x1e, 0x0b, 0xd5, 0x9b, 0xaa, 0xff, 0xee, 0xfe, 0x2f, 0x99, 0x72, 0x4c, 0x71, 0x9d, 0x47, 0xa2, 0xec, 0xba, 0x72, 0x1d, 0x76, 0xf2, 0x37, 0xeb, 0xa7, 0x3d, 0xb4, 0x7d, 0x88, + 0xb6, 0x99, 0xe3, 0x58, 0x2b, 0x07, 0x3c, 0x7e, 0xad, 0x2a, 0x5b, 0x3c, 0xf0, 0x24, 0x46, 0x63, 0x96, 0xf9, 0xf2, 0x82, 0x6c, 0xb7, 0x54, 0xf6, 0x60, 0x18, 0xe9, 0x50, 0x3f, 0x4a, 0xd1, 0xf9, + 0xd9, 0x21, 0x21, 0xaa, 0x99, 0x56, 0x50, 0x60, 0x51, 0xd5, 0x96, 0xff, 0xd4, 0x67, 0xe1, 0xaa, 0x8d, 0x96, 0x4c, 0x17, 0x67, 0xc9, 0x25, 0xb4, 0x68, 0xbb, 0xc9, 0x85, 0x06, 0x00, 0xc8, 0x43, + 0x49, 0x05, 0x41, 0xe8, 0x55, 0x5a, 0x3d, 0x8b, 0xd9, 0xf1, 0x87, 0x91, 0xef, 0x9e, 0xbd, 0x35, 0x94, 0xe7, 0x4c, 0x1f, 0xe3, 0xd3, 0xb8, 0x09, 0x40, 0xa8, 0xa0, 0x79, 0xf8, 0xd2, 0xca, 0x8d, + 0x30, 0x13, 0x4f, 0xc6, 0x6f, 0x87, 0x00, 0x81, 0x26, 0xe4, 0x3b, 0xd0, 0x6e, 0xb6, 0xe4, 0x1c, 0x3a, 0x70, 0xfa, 0x47, 0x39, 0x31, 0x9b, 0xf1, 0xa9, 0x32, 0xf0, 0x2c, 0x30, 0x64, 0x56, 0x56, + 0x0c, 0xda, 0x44, 0xdd, 0xac, 0x43, 0xed, 0x6d, 0x90, 0x04, 0x45, 0xf5, 0xbf, 0x85, 0xbb, 0x0c, 0xe3, 0x25, 0x94, 0x74, 0x36, 0xe0, 0xd0, 0x68, 0x5e, 0x41, 0xb1, 0x6b, 0xc7, 0x16, 0x95, 0x18, + 0x25, 0x9e, 0x57, 0x34, 0xfd, 0xce, 0x08, 0x0f, 0xfe, 0x85, 0x19, 0x1b, 0x1d, 0x8d, 0x8d, 0xe4, 0xdb, 0x48, 0x14, 0x3f, 0xb5, 0x64, 0x03, 0x8a, 0xce, 0x80, 0x10, 0x4d, 0x3a, 0x8d, 0x07, 0x12, + 0x45, 0xe2, 0xaa, 0x56, 0xc7, 0x19, 0x33, 0xf4, 0xdc, 0xf9, 0x25, 0xee, 0xe8, 0x44, 0xc8, 0x0f, 0xdd, 0xf3, 0x25, 0x1f, 0x74, 0x00, 0x6a, 0x23, 0x41, 0x33, 0x18, 0xbb, 0xfd, 0x2e, 0xd9, 0xe0, + 0x53, 0x51, 0xb5, 0xaa, 0xeb, 0xcc, 0x77, 0xcf, 0xac, 0x8d, 0x5f, 0x03, 0x64, 0x23, 0x1a, 0x50, 0xea, 0x86, 0x47, 0xc7, 0x2f, 0x71, 0x3e, 0x81, 0x7a, 0x20, 0x75, 0x32, 0x30, 0x29, 0xe3, 0xb8, + 0x8b, 0x72, 0x44, 0x22, 0x64, 0xc5, 0x97, 0xb0, 0xf1, 0xfc, 0x09, 0xf9, 0x40, 0x1c, 0xe8, 0x8a, 0xc9, 0x7c, 0x55, 0x22, 0xa5, 0x63, 0x64, 0x52, 0x3c, 0x37, 0xfe, 0xa2, 0xd6, 0xbd, 0x06, 0xb2, + }, + }, + { + .name = "Kyber Round 2, 1024 KAT 0", + .version = 0, + .keyform = CK_IBM_KYBER_KEYFORM_ROUND2_1024, + .sk_len = 3168, + .sk = { + 0x07, 0x63, 0x8F, 0xB6, 0x98, 0x68, 0xF3, 0xD3, 0x20, 0xE5, 0x86, 0x2B, 0xD9, 0x69, 0x33, 0xFE, 0xB3, 0x11, 0xB3, 0x62, 0x09, 0x3C, 0x9B, 0x5D, 0x50, 0x17, 0x0B, 0xCE, 0xD4, 0x3F, 0x1B, 0x53, + 0x6D, 0x9A, 0x20, 0x4B, 0xB1, 0xF2, 0x26, 0x95, 0x95, 0x0B, 0xA1, 0xF2, 0xA9, 0xE8, 0xEB, 0x82, 0x8B, 0x28, 0x44, 0x88, 0x76, 0x0B, 0x3F, 0xC8, 0x4F, 0xAB, 0xA0, 0x42, 0x75, 0xD5, 0x62, 0x8E, + 0x39, 0xC5, 0xB2, 0x47, 0x13, 0x74, 0x28, 0x3C, 0x50, 0x32, 0x99, 0xC0, 0xAB, 0x49, 0xB6, 0x6B, 0x8B, 0xBB, 0x56, 0xA4, 0x18, 0x66, 0x24, 0xF9, 0x19, 0xA2, 0xBA, 0x59, 0xBB, 0x08, 0xD8, 0x55, + 0x18, 0x80, 0xC2, 0xBE, 0xFC, 0x4F, 0x87, 0xF2, 0x5F, 0x59, 0xAB, 0x58, 0x7A, 0x79, 0xC3, 0x27, 0xD7, 0x92, 0xD5, 0x4C, 0x97, 0x4A, 0x69, 0x26, 0x2F, 0xF8, 0xA7, 0x89, 0x38, 0x28, 0x9E, 0x9A, + 0x87, 0xB6, 0x88, 0xB0, 0x83, 0xE0, 0x59, 0x5F, 0xE2, 0x18, 0xB6, 0xBB, 0x15, 0x05, 0x94, 0x1C, 0xE2, 0xE8, 0x1A, 0x5A, 0x64, 0xC5, 0xAA, 0xC6, 0x04, 0x17, 0x25, 0x69, 0x85, 0x34, 0x9E, 0xE4, + 0x7A, 0x52, 0x42, 0x0A, 0x5F, 0x97, 0x47, 0x7B, 0x72, 0x36, 0xAC, 0x76, 0xBC, 0x70, 0xE8, 0x28, 0x87, 0x29, 0x28, 0x7E, 0xE3, 0xE3, 0x4A, 0x3D, 0xBC, 0x36, 0x83, 0xC0, 0xB7, 0xB1, 0x00, 0x29, + 0xFC, 0x20, 0x34, 0x18, 0x53, 0x7E, 0x74, 0x66, 0xBA, 0x63, 0x85, 0xA8, 0xFF, 0x30, 0x1E, 0xE1, 0x27, 0x08, 0xF8, 0x2A, 0xAA, 0x1E, 0x38, 0x0F, 0xC7, 0xA8, 0x8F, 0x8F, 0x20, 0x5A, 0xB7, 0xE8, + 0x8D, 0x7E, 0x95, 0x95, 0x2A, 0x55, 0xBA, 0x20, 0xD0, 0x9B, 0x79, 0xA4, 0x71, 0x41, 0xD6, 0x2B, 0xF6, 0xEB, 0x7D, 0xD3, 0x07, 0xB0, 0x8E, 0xCA, 0x13, 0xA5, 0xBC, 0x5F, 0x6B, 0x68, 0x58, 0x1C, + 0x68, 0x65, 0xB2, 0x7B, 0xBC, 0xDD, 0xAB, 0x14, 0x2F, 0x4B, 0x2C, 0xBF, 0xF4, 0x88, 0xC8, 0xA2, 0x27, 0x05, 0xFA, 0xA9, 0x8A, 0x2B, 0x9E, 0xEA, 0x35, 0x30, 0xC7, 0x66, 0x62, 0x33, 0x5C, 0xC7, + 0xEA, 0x3A, 0x00, 0x77, 0x77, 0x25, 0xEB, 0xCC, 0xCD, 0x2A, 0x46, 0x36, 0xB2, 0xD9, 0x12, 0x2F, 0xF3, 0xAB, 0x77, 0x12, 0x3C, 0xE0, 0x88, 0x3C, 0x19, 0x11, 0x11, 0x5E, 0x50, 0xC9, 0xE8, 0xA9, + 0x41, 0x94, 0xE4, 0x8D, 0xD0, 0xD0, 0x9C, 0xFF, 0xB3, 0xAD, 0xCD, 0x2C, 0x1E, 0x92, 0x43, 0x09, 0x03, 0xD0, 0x7A, 0xDB, 0xF0, 0x05, 0x32, 0x03, 0x15, 0x75, 0xAA, 0x7F, 0x9E, 0x7B, 0x5A, 0x1F, + 0x33, 0x62, 0xDE, 0xC9, 0x36, 0xD4, 0x04, 0x3C, 0x05, 0xF2, 0x47, 0x6C, 0x07, 0x57, 0x8B, 0xC9, 0xCB, 0xAF, 0x2A, 0xB4, 0xE3, 0x82, 0x72, 0x7A, 0xD4, 0x16, 0x86, 0xA9, 0x6B, 0x25, 0x48, 0x82, + 0x0B, 0xB0, 0x3B, 0x32, 0xF1, 0x1B, 0x28, 0x11, 0xAD, 0x62, 0xF4, 0x89, 0xE9, 0x51, 0x63, 0x2A, 0xBA, 0x0D, 0x1D, 0xF8, 0x96, 0x80, 0xCC, 0x8A, 0x8B, 0x53, 0xB4, 0x81, 0xD9, 0x2A, 0x68, 0xD7, + 0x0B, 0x4E, 0xA1, 0xC3, 0xA6, 0xA5, 0x61, 0xC0, 0x69, 0x28, 0x82, 0xB5, 0xCA, 0x8C, 0xC9, 0x42, 0xA8, 0xD4, 0x95, 0xAF, 0xCB, 0x06, 0xDE, 0x89, 0x49, 0x8F, 0xB9, 0x35, 0xB7, 0x75, 0x90, 0x8F, + 0xE7, 0xA0, 0x3E, 0x32, 0x4D, 0x54, 0xCC, 0x19, 0xD4, 0xE1, 0xAA, 0xBD, 0x35, 0x93, 0xB3, 0x8B, 0x19, 0xEE, 0x13, 0x88, 0xFE, 0x49, 0x2B, 0x43, 0x12, 0x7E, 0x5A, 0x50, 0x42, 0x53, 0x78, 0x6A, + 0x0D, 0x69, 0xAD, 0x32, 0x60, 0x1C, 0x28, 0xE2, 0xC8, 0x85, 0x04, 0xA5, 0xBA, 0x59, 0x97, 0x06, 0x02, 0x3A, 0x61, 0x36, 0x3E, 0x17, 0xC6, 0xB9, 0xBB, 0x59, 0xBD, 0xC6, 0x97, 0x45, 0x2C, 0xD0, + 0x59, 0x45, 0x19, 0x83, 0xD7, 0x38, 0xCA, 0x3F, 0xD0, 0x34, 0xE3, 0xF5, 0x98, 0x88, 0x54, 0xCA, 0x05, 0x03, 0x1D, 0xB0, 0x96, 0x11, 0x49, 0x89, 0x88, 0x19, 0x7C, 0x6B, 0x30, 0xD2, 0x58, 0xDF, + 0xE2, 0x62, 0x65, 0x54, 0x1C, 0x89, 0xA4, 0xB3, 0x1D, 0x68, 0x64, 0xE9, 0x38, 0x9B, 0x03, 0xCB, 0x74, 0xF7, 0xEC, 0x43, 0x23, 0xFB, 0x94, 0x21, 0xA4, 0xB9, 0x79, 0x0A, 0x26, 0xD1, 0x7B, 0x03, + 0x98, 0xA2, 0x67, 0x67, 0x35, 0x09, 0x09, 0xF8, 0x4D, 0x57, 0xB6, 0x69, 0x4D, 0xF8, 0x30, 0x66, 0x4C, 0xA8, 0xB3, 0xC3, 0xC0, 0x3E, 0xD2, 0xAE, 0x67, 0xB8, 0x90, 0x06, 0x86, 0x8A, 0x68, 0x52, + 0x7C, 0xCD, 0x66, 0x64, 0x59, 0xAB, 0x7F, 0x05, 0x66, 0x71, 0x00, 0x0C, 0x61, 0x64, 0xD3, 0xA7, 0xF2, 0x66, 0xA1, 0x4D, 0x97, 0xCB, 0xD7, 0x00, 0x4D, 0x6C, 0x92, 0xCA, 0xCA, 0x77, 0x0B, 0x84, + 0x4A, 0x4F, 0xA9, 0xB1, 0x82, 0xE7, 0xB1, 0x8C, 0xA8, 0x85, 0x08, 0x2A, 0xC5, 0x64, 0x6F, 0xCB, 0x4A, 0x14, 0xE1, 0x68, 0x5F, 0xEB, 0x0C, 0x9C, 0xE3, 0x37, 0x2A, 0xB9, 0x53, 0x65, 0xC0, 0x4F, + 0xD8, 0x30, 0x84, 0xF8, 0x0A, 0x23, 0xFF, 0x10, 0xA0, 0x5B, 0xF1, 0x5F, 0x7F, 0xA5, 0xAC, 0xC6, 0xC0, 0xCB, 0x46, 0x2C, 0x33, 0xCA, 0x52, 0x4F, 0xA6, 0xB8, 0xBB, 0x35, 0x90, 0x43, 0xBA, 0x68, + 0x60, 0x9E, 0xAA, 0x25, 0x36, 0xE8, 0x1D, 0x08, 0x46, 0x3B, 0x19, 0x65, 0x3B, 0x54, 0x35, 0xBA, 0x94, 0x6C, 0x9A, 0xDD, 0xEB, 0x20, 0x2B, 0x04, 0xB0, 0x31, 0xCC, 0x96, 0x0D, 0xCC, 0x12, 0xE4, + 0x51, 0x8D, 0x42, 0x8B, 0x32, 0xB2, 0x57, 0xA4, 0xFC, 0x73, 0x13, 0xD3, 0xA7, 0x98, 0x0D, 0x80, 0x08, 0x2E, 0x93, 0x4F, 0x9D, 0x95, 0xC3, 0x2B, 0x0A, 0x01, 0x91, 0xA2, 0x36, 0x04, 0x38, 0x4D, + 0xD9, 0xE0, 0x79, 0xBB, 0xBA, 0xA2, 0x66, 0xD1, 0x4C, 0x3F, 0x75, 0x6B, 0x9F, 0x21, 0x33, 0x10, 0x74, 0x33, 0xA4, 0xE8, 0x3F, 0xA7, 0x18, 0x72, 0x82, 0xA8, 0x09, 0x20, 0x3A, 0x4F, 0xAF, 0x84, + 0x18, 0x51, 0x83, 0x3D, 0x12, 0x1A, 0xC3, 0x83, 0x84, 0x3A, 0x5E, 0x55, 0xBC, 0x23, 0x81, 0x42, 0x5E, 0x16, 0xC7, 0xDB, 0x4C, 0xC9, 0xAB, 0x5C, 0x1B, 0x0D, 0x91, 0xA4, 0x7E, 0x2B, 0x8D, 0xE0, + 0xE5, 0x82, 0xC8, 0x6B, 0x6B, 0x0D, 0x90, 0x7B, 0xB3, 0x60, 0xB9, 0x7F, 0x40, 0xAB, 0x5D, 0x03, 0x8F, 0x6B, 0x75, 0xC8, 0x14, 0xB2, 0x7D, 0x9B, 0x96, 0x8D, 0x41, 0x98, 0x32, 0xBC, 0x8C, 0x2B, + 0xEE, 0x60, 0x5E, 0xF6, 0xE5, 0x05, 0x9D, 0x33, 0x10, 0x0D, 0x90, 0x48, 0x5D, 0x37, 0x84, 0x50, 0x01, 0x42, 0x21, 0x73, 0x6C, 0x07, 0x40, 0x7C, 0xAC, 0x26, 0x04, 0x08, 0xAA, 0x64, 0x92, 0x66, + 0x19, 0x78, 0x8B, 0x86, 0x01, 0xC2, 0xA7, 0x52, 0xD1, 0xA6, 0xCB, 0xF8, 0x20, 0xD7, 0xC7, 0xA0, 0x47, 0x16, 0x20, 0x32, 0x25, 0xB3, 0x89, 0x5B, 0x93, 0x42, 0xD1, 0x47, 0xA8, 0x18, 0x5C, 0xFC, + 0x1B, 0xB6, 0x5B, 0xA0, 0x6B, 0x41, 0x42, 0x33, 0x99, 0x03, 0xC0, 0xAC, 0x46, 0x51, 0x38, 0x5B, 0x45, 0xD9, 0x8A, 0x8B, 0x19, 0xD2, 0x8C, 0xD6, 0xBA, 0xB0, 0x88, 0x78, 0x7F, 0x7E, 0xE1, 0xB1, + 0x24, 0x61, 0x76, 0x6B, 0x43, 0xCB, 0xCC, 0xB9, 0x64, 0x34, 0x42, 0x7D, 0x93, 0xC0, 0x65, 0x55, 0x06, 0x88, 0xF6, 0x94, 0x8E, 0xD1, 0xB5, 0x47, 0x5A, 0x42, 0x5F, 0x1B, 0x85, 0x20, 0x9D, 0x06, + 0x1C, 0x08, 0xB5, 0x6C, 0x1C, 0xC0, 0x69, 0xF6, 0xC0, 0xA7, 0xC6, 0xF2, 0x93, 0x58, 0xCA, 0xB9, 0x11, 0x08, 0x77, 0x32, 0xA6, 0x49, 0xD2, 0x7C, 0x9B, 0x98, 0xF9, 0xA4, 0x88, 0x79, 0x38, 0x7D, + 0x9B, 0x00, 0xC2, 0x59, 0x59, 0xA7, 0x16, 0x54, 0xD6, 0xF6, 0xA9, 0x46, 0x16, 0x45, 0x13, 0xE4, 0x7A, 0x75, 0xD0, 0x05, 0x98, 0x6C, 0x23, 0x63, 0xC0, 0x9F, 0x6B, 0x53, 0x7E, 0xCA, 0x78, 0xB9, + 0x30, 0x3A, 0x5F, 0xA4, 0x57, 0x60, 0x8A, 0x58, 0x6A, 0x65, 0x3A, 0x34, 0x7D, 0xB0, 0x4D, 0xFC, 0xC1, 0x91, 0x75, 0xB3, 0xA3, 0x01, 0x17, 0x25, 0x36, 0x06, 0x2A, 0x65, 0x8A, 0x95, 0x27, 0x75, + 0x70, 0xC8, 0x85, 0x2C, 0xA8, 0x97, 0x3F, 0x4A, 0xE1, 0x23, 0xA3, 0x34, 0x04, 0x7D, 0xD7, 0x11, 0xC8, 0x92, 0x7A, 0x63, 0x4A, 0x03, 0x38, 0x8A, 0x52, 0x7B, 0x03, 0x4B, 0xF7, 0xA8, 0x17, 0x0F, + 0xA7, 0x02, 0xC1, 0xF7, 0xC2, 0x3E, 0xC3, 0x2D, 0x18, 0xA2, 0x37, 0x48, 0x90, 0xBE, 0x9C, 0x78, 0x7A, 0x94, 0x09, 0xC8, 0x2D, 0x19, 0x2C, 0x4B, 0xB7, 0x05, 0xA2, 0xF9, 0x96, 0xCE, 0x40, 0x5D, + 0x85, 0xA4, 0xC1, 0xA1, 0xAB, 0x9B, 0x6A, 0xEB, 0x49, 0xCC, 0xE1, 0xC2, 0xF8, 0xA9, 0x7C, 0x35, 0x16, 0xC7, 0x2A, 0x00, 0xA4, 0x62, 0x63, 0xBA, 0xA6, 0x96, 0xBF, 0x25, 0x72, 0x77, 0x19, 0xC3, + 0x21, 0x64, 0x23, 0x61, 0x8F, 0xF3, 0x33, 0x80, 0x93, 0x4A, 0x6C, 0x10, 0x54, 0x5C, 0x4C, 0x5C, 0x51, 0x55, 0xB1, 0x24, 0x86, 0x18, 0x1F, 0xC7, 0xA2, 0x31, 0x98, 0x73, 0x97, 0x8B, 0x6A, 0x2A, + 0x67, 0x49, 0x0F, 0x82, 0x56, 0xBD, 0x21, 0x96, 0xFE, 0x17, 0x92, 0xA4, 0xC0, 0x00, 0x77, 0xB8, 0x12, 0xEA, 0xE8, 0xBE, 0xD3, 0x57, 0x24, 0x99, 0x68, 0x4A, 0xB3, 0x37, 0x18, 0x76, 0x76, 0x1E, + 0x45, 0x0C, 0x9F, 0x9D, 0x27, 0x68, 0xA3, 0x68, 0x06, 0xD7, 0xAB, 0x20, 0x46, 0xC9, 0x1F, 0x17, 0x59, 0x9E, 0x9A, 0xC5, 0x92, 0x99, 0x08, 0x08, 0xDC, 0xD7, 0xB4, 0xD0, 0x91, 0x90, 0x72, 0xF1, + 0x4E, 0xC3, 0x61, 0x77, 0x3B, 0x72, 0x52, 0x44, 0x4C, 0x32, 0x3C, 0x30, 0x83, 0x26, 0xF4, 0xA3, 0x0F, 0x86, 0x80, 0xD2, 0xF7, 0x48, 0xF5, 0x6A, 0x13, 0x2B, 0x82, 0x67, 0x4E, 0xD0, 0x18, 0x46, + 0x20, 0xB8, 0x2A, 0xD2, 0xCB, 0x18, 0x2C, 0x97, 0xB4, 0x81, 0x62, 0x66, 0x47, 0x49, 0x12, 0x90, 0xA0, 0x11, 0xCC, 0x73, 0x82, 0x86, 0x85, 0xA8, 0xC3, 0x67, 0xA5, 0xB9, 0xCF, 0x8D, 0x62, 0x1B, + 0x0D, 0x5C, 0x1E, 0xFF, 0x03, 0x17, 0x27, 0x58, 0xBD, 0x00, 0x49, 0x78, 0xC2, 0x51, 0xCD, 0x51, 0x34, 0x22, 0x28, 0x98, 0x9C, 0xAE, 0x63, 0x32, 0xAC, 0x48, 0x64, 0x37, 0xCB, 0x5C, 0x57, 0xD4, + 0x30, 0x74, 0x62, 0x86, 0x52, 0x53, 0xBE, 0x21, 0x7B, 0x35, 0x15, 0xC7, 0x3D, 0xF4, 0x05, 0xB7, 0xF2, 0x82, 0x17, 0xAD, 0x0B, 0x8C, 0xF6, 0x0C, 0x2F, 0xFF, 0xAA, 0x0A, 0x00, 0x48, 0xB1, 0xFB, + 0x4A, 0xCD, 0xCD, 0xC3, 0x8B, 0x52, 0x50, 0xCF, 0xEC, 0x35, 0x6A, 0x6D, 0xE2, 0x6C, 0xFA, 0x7A, 0x58, 0x8F, 0xDC, 0x86, 0xF9, 0x8C, 0x85, 0x4A, 0xC6, 0x4C, 0x7B, 0xFA, 0xA9, 0x6F, 0x5A, 0x32, + 0xCC, 0x06, 0x10, 0x93, 0x4B, 0xAA, 0x6A, 0x58, 0x6B, 0x9A, 0x20, 0x54, 0xF1, 0x3B, 0xA2, 0x74, 0x17, 0x4A, 0xA0, 0xD2, 0xB3, 0xA8, 0x1B, 0x96, 0xA9, 0x40, 0x66, 0x6F, 0x78, 0x9B, 0x5A, 0x6B, + 0xCD, 0xC0, 0xA6, 0xA0, 0x17, 0x8A, 0x0C, 0x9A, 0x02, 0x57, 0x8A, 0x49, 0x3F, 0x6E, 0xEA, 0x0D, 0x2E, 0x6C, 0x13, 0x95, 0x1C, 0x9F, 0x24, 0x9A, 0x5E, 0x8D, 0xD7, 0x1D, 0xD4, 0x9A, 0x74, 0x2D, + 0x45, 0x1F, 0x1A, 0xBB, 0xA1, 0x9A, 0xF8, 0xC5, 0x47, 0x85, 0x5E, 0x0A, 0xFC, 0x72, 0x8E, 0x90, 0xAB, 0xB4, 0x99, 0xC9, 0xBE, 0xEB, 0x76, 0x6F, 0x47, 0x29, 0xCD, 0xA2, 0x22, 0x63, 0xE3, 0x24, + 0xDA, 0x18, 0x71, 0x2D, 0x31, 0x6E, 0x98, 0xDC, 0x7A, 0xC8, 0xC3, 0xCA, 0x47, 0x37, 0x0E, 0xBD, 0x77, 0x0C, 0xE3, 0x2B, 0x3B, 0xD4, 0xB1, 0xA0, 0xC9, 0x52, 0x9A, 0xC6, 0xEC, 0x8E, 0xE0, 0x28, + 0xB1, 0xCD, 0xB2, 0x65, 0x1C, 0xB5, 0xA6, 0xBB, 0x3C, 0x0C, 0x6D, 0xF1, 0x24, 0x0A, 0x3B, 0x91, 0x4B, 0x56, 0x56, 0xC0, 0xDC, 0x51, 0xC2, 0xB9, 0x1B, 0xFC, 0xBC, 0x37, 0xA4, 0x66, 0x02, 0x87, + 0xD4, 0x4F, 0x81, 0xF8, 0x53, 0xC7, 0xF4, 0x9A, 0x6D, 0x06, 0x03, 0xD6, 0xD7, 0x23, 0xCB, 0xEC, 0x01, 0x5F, 0xBC, 0x43, 0x4A, 0x38, 0x24, 0x1C, 0x10, 0x9C, 0x7E, 0xD5, 0xB1, 0xCC, 0x46, 0x1A, + 0x2C, 0xCB, 0x9A, 0xB7, 0x14, 0x0F, 0x19, 0xF3, 0x7A, 0x13, 0xBB, 0x70, 0x1E, 0x14, 0x2B, 0xD5, 0x4B, 0x64, 0xEC, 0x6B, 0x76, 0xFE, 0xC3, 0x3B, 0x69, 0xC2, 0x91, 0x8C, 0xB0, 0x17, 0xC4, 0x14, + 0x34, 0x23, 0x00, 0x9A, 0x3C, 0x07, 0xB5, 0xC1, 0x81, 0xB0, 0xC1, 0xEB, 0x49, 0x4A, 0x62, 0xAB, 0xC8, 0x39, 0x13, 0x97, 0x08, 0x9E, 0xA6, 0x64, 0x09, 0x67, 0xC1, 0x20, 0x49, 0x84, 0xCD, 0x48, + 0x4C, 0xCC, 0xB0, 0x0A, 0x9A, 0x17, 0xD0, 0x87, 0x21, 0x84, 0x28, 0xEF, 0x3B, 0xB7, 0x08, 0x78, 0x3E, 0x12, 0x82, 0x71, 0x04, 0x41, 0x73, 0x75, 0xB6, 0x95, 0x6F, 0xB5, 0x00, 0x53, 0xD0, 0x48, + 0xA4, 0x79, 0x14, 0x95, 0x82, 0x4A, 0x34, 0x80, 0xA5, 0xB7, 0x83, 0x02, 0x56, 0x09, 0x6F, 0xDD, 0x72, 0x5C, 0x30, 0x8B, 0x3B, 0xE8, 0x4A, 0x07, 0xF3, 0x63, 0x2E, 0x24, 0x95, 0xC6, 0x2E, 0x96, + 0x39, 0x9D, 0x80, 0xBF, 0xA7, 0x45, 0xB9, 0x84, 0x1A, 0x18, 0x33, 0xBC, 0x1D, 0x27, 0xBA, 0x45, 0xA5, 0x21, 0x68, 0xEE, 0x59, 0x00, 0x6C, 0x3A, 0x3A, 0x8C, 0x4A, 0x5A, 0x4F, 0x50, 0x88, 0xFC, + 0x73, 0x71, 0x81, 0xAB, 0x51, 0x96, 0xF7, 0xB1, 0xB4, 0x9A, 0x2E, 0xD8, 0x13, 0x13, 0x4E, 0x11, 0x2F, 0x73, 0x0B, 0x99, 0x1C, 0x54, 0xA7, 0x19, 0x6B, 0xCF, 0x5F, 0xC7, 0x6E, 0x13, 0x4C, 0x58, + 0x43, 0xE1, 0x69, 0x88, 0x51, 0xB2, 0xF8, 0x69, 0xAF, 0xAF, 0xB0, 0x27, 0x87, 0xD9, 0xC2, 0xF1, 0x36, 0x90, 0x2D, 0xC7, 0xA7, 0xF3, 0xD6, 0x21, 0x56, 0xD1, 0x5E, 0xC3, 0x09, 0x56, 0x40, 0x92, + 0xC6, 0x1D, 0x83, 0xB0, 0x98, 0x6C, 0x48, 0x40, 0x99, 0x81, 0xF3, 0xC1, 0x86, 0x88, 0x0A, 0x2F, 0x63, 0xD5, 0x86, 0x0A, 0xB6, 0x01, 0xDE, 0xAC, 0x2B, 0x6B, 0xA1, 0xB4, 0x28, 0x17, 0x9D, 0x73, + 0x53, 0x3E, 0xB7, 0xA3, 0xA5, 0x11, 0x3B, 0x85, 0x61, 0xF1, 0x0B, 0x45, 0xC3, 0xCD, 0xE2, 0x82, 0xB6, 0xEA, 0xD6, 0xAB, 0x6C, 0x60, 0x4F, 0x09, 0xC1, 0x7B, 0xFD, 0xA0, 0x83, 0x13, 0xA3, 0x26, + 0x07, 0x67, 0x5A, 0xDF, 0x64, 0x31, 0xCA, 0x87, 0x18, 0xE9, 0xC4, 0x3A, 0x73, 0x73, 0x32, 0x27, 0xE7, 0x3B, 0xC6, 0x1A, 0xC8, 0x45, 0xBA, 0x90, 0x77, 0x55, 0xCE, 0xC6, 0x89, 0x25, 0xE5, 0xE2, + 0xBF, 0xE9, 0x12, 0x95, 0x9D, 0xB8, 0x6F, 0xBF, 0xE2, 0x15, 0x6F, 0xD5, 0xBB, 0xDB, 0xF0, 0xC9, 0xDF, 0x8B, 0x53, 0x02, 0xAA, 0x8D, 0x90, 0xA2, 0x2D, 0x12, 0x27, 0x0E, 0x00, 0x65, 0x51, 0xE4, + 0x76, 0x7E, 0x45, 0x26, 0x8E, 0xD9, 0x69, 0x26, 0x54, 0x44, 0x78, 0x11, 0xEA, 0xB8, 0x4F, 0x04, 0x99, 0xA8, 0xA5, 0x8C, 0xF7, 0xC0, 0x4A, 0x59, 0x56, 0x98, 0x52, 0x80, 0x45, 0xF2, 0x98, 0x97, + 0xC8, 0xFA, 0x96, 0xD0, 0x6C, 0xCE, 0x51, 0xE6, 0xAF, 0xEA, 0xC4, 0x33, 0x95, 0x89, 0xC9, 0x41, 0xC8, 0x55, 0x63, 0xD7, 0x0F, 0xAC, 0xE1, 0x92, 0x88, 0x94, 0xBA, 0xC0, 0x36, 0x19, 0xDF, 0xF4, + 0xBE, 0x3F, 0x43, 0x14, 0xA3, 0xF7, 0x35, 0x1A, 0x09, 0xA4, 0x86, 0xB5, 0x04, 0x1E, 0x7C, 0xB2, 0xDA, 0x8B, 0x96, 0xBC, 0x66, 0x26, 0xA4, 0x93, 0x17, 0x35, 0x7C, 0x41, 0x52, 0xA5, 0x1B, 0xA3, + 0xC2, 0x8C, 0x7E, 0x0C, 0x9D, 0xB4, 0x1A, 0x06, 0xA2, 0x82, 0x90, 0xF2, 0x18, 0x73, 0x11, 0x07, 0xC9, 0x54, 0xD8, 0xA6, 0x6F, 0x80, 0x1D, 0x7D, 0xE1, 0x2A, 0x03, 0x71, 0x16, 0x99, 0x0B, 0x6C, + 0x53, 0xC1, 0x29, 0xF1, 0x85, 0xC3, 0x45, 0xF2, 0x7E, 0x51, 0x8B, 0x2D, 0x5A, 0x91, 0x25, 0xA0, 0x70, 0x76, 0xD9, 0x91, 0xB7, 0xDA, 0xC7, 0xCC, 0x65, 0xA8, 0x56, 0x2E, 0xFB, 0xCC, 0x32, 0xA9, + 0xCA, 0x4A, 0xD9, 0x02, 0x63, 0xB0, 0x4A, 0x4F, 0x90, 0x36, 0x11, 0x6C, 0x7B, 0x97, 0x48, 0x04, 0x96, 0x31, 0x75, 0x75, 0x65, 0x0D, 0xCC, 0x21, 0x52, 0xB5, 0xBC, 0x0E, 0x74, 0x40, 0x7E, 0x12, + 0xFA, 0x8E, 0x4F, 0xFC, 0xCC, 0xFF, 0x76, 0xC0, 0x1A, 0x97, 0x4B, 0xD6, 0x11, 0x02, 0xE1, 0xF5, 0x29, 0x64, 0x96, 0xC7, 0x1D, 0x07, 0x64, 0xE1, 0x32, 0x29, 0xFF, 0xE7, 0x84, 0x6F, 0x33, 0x6E, + 0x34, 0xCA, 0xC9, 0x04, 0xCA, 0x56, 0x70, 0xF8, 0xCD, 0x50, 0x52, 0x42, 0x7A, 0x79, 0xC0, 0x91, 0xA9, 0x71, 0x21, 0x0C, 0x5C, 0xFF, 0x66, 0x7A, 0xAC, 0x24, 0x93, 0x66, 0xE1, 0x0D, 0x2B, 0x11, + 0x37, 0x6C, 0xA3, 0x9D, 0x93, 0x52, 0x04, 0xB1, 0x2C, 0xC5, 0x85, 0xE9, 0x40, 0x54, 0x03, 0x62, 0x5F, 0xB3, 0x2C, 0xB5, 0xE5, 0xC3, 0x1B, 0x62, 0x34, 0x81, 0x60, 0x51, 0x5C, 0xCC, 0x4F, 0xDA, + 0xF5, 0x70, 0x2D, 0x6B, 0xAB, 0x5C, 0x37, 0x3D, 0xB6, 0xF3, 0x50, 0xD3, 0xE6, 0x3A, 0x5C, 0xE3, 0xCA, 0x54, 0x74, 0xA0, 0xCF, 0x15, 0x67, 0x04, 0x2C, 0xA3, 0x25, 0x89, 0x86, 0xFF, 0x75, 0xBD, + 0xFC, 0xD9, 0x29, 0xE6, 0x46, 0x2F, 0x36, 0xBC, 0xCC, 0x3F, 0x5A, 0x93, 0x35, 0x2A, 0x2B, 0x36, 0xCB, 0x16, 0x2E, 0x18, 0x74, 0xC7, 0x42, 0x87, 0x0A, 0x97, 0xB1, 0x67, 0xA0, 0x50, 0x37, 0x36, + 0x24, 0xEA, 0xEB, 0x7E, 0x50, 0x73, 0x25, 0x6B, 0x72, 0x11, 0xB2, 0xD9, 0x4B, 0x84, 0x06, 0xCD, 0x6C, 0x95, 0x33, 0xB1, 0x53, 0x64, 0x08, 0xAB, 0x0A, 0x29, 0xE5, 0xB2, 0xF0, 0xC9, 0x54, 0xEC, + 0xE0, 0x0F, 0xBB, 0xEB, 0x17, 0x6D, 0x72, 0x4D, 0x4C, 0xF4, 0x43, 0xCF, 0x70, 0x20, 0xD5, 0xFA, 0x70, 0x94, 0xCC, 0x1B, 0x1B, 0xE6, 0x97, 0xBA, 0xD3, 0x36, 0x74, 0xE4, 0x09, 0x9E, 0xC7, 0xBB, + 0x18, 0xF4, 0x57, 0x71, 0x28, 0xCD, 0xD9, 0x7C, 0xCD, 0x6D, 0x44, 0x62, 0xE5, 0x60, 0x7C, 0x51, 0x2A, 0x3E, 0x36, 0x24, 0x8E, 0x3D, 0xDA, 0xA2, 0xEC, 0x08, 0x9A, 0xEF, 0xC4, 0xCE, 0x48, 0x5C, + 0x49, 0xD7, 0xB0, 0x09, 0xC8, 0xD6, 0x31, 0x15, 0xFC, 0x81, 0xFF, 0x3A, 0x62, 0xD1, 0x5A, 0x88, 0x44, 0x1C, 0x03, 0xEA, 0x1C, 0x2E, 0x72, 0xC4, 0x88, 0x39, 0xFC, 0x6A, 0xD7, 0x3A, 0x30, 0x74, + 0x4A, 0x62, 0xB7, 0xB2, 0x16, 0x45, 0xA6, 0xAF, 0x7D, 0x61, 0xB6, 0x38, 0x3B, 0x22, 0x1E, 0x21, 0x90, 0x55, 0x57, 0xCD, 0x29, 0xD9, 0x24, 0xA6, 0x09, 0x86, 0xC5, 0x11, 0xC1, 0xEB, 0xBC, 0x31, + 0x6D, 0x56, 0x30, 0xA2, 0x41, 0x43, 0x23, 0xF5, 0x3A, 0xD5, 0x59, 0x94, 0xF6, 0xB3, 0x65, 0x39, 0xF9, 0xC4, 0x40, 0x75, 0xA5, 0x33, 0xE4, 0x81, 0xC0, 0x84, 0x45, 0xD9, 0xCA, 0x9E, 0x9D, 0x38, + 0x21, 0x19, 0x38, 0x8B, 0xD1, 0xD7, 0x50, 0x52, 0x21, 0x7A, 0x94, 0x4C, 0xCC, 0x7B, 0xE9, 0x09, 0xE2, 0x19, 0x71, 0x1F, 0xCC, 0x79, 0x24, 0x76, 0x92, 0x13, 0xA1, 0x92, 0x53, 0x4A, 0x55, 0x80, + 0x08, 0x15, 0x7A, 0x39, 0x6E, 0xDF, 0xF4, 0x80, 0xCC, 0x3B, 0x52, 0x0F, 0xF8, 0x18, 0xB3, 0x8B, 0x13, 0x5C, 0x18, 0xA8, 0x0D, 0x51, 0x05, 0xE6, 0x78, 0x83, 0x6C, 0x39, 0x5C, 0x28, 0xE9, 0x2F, + 0x7A, 0x3C, 0x4E, 0x93, 0xC0, 0x10, 0x35, 0xF3, 0x41, 0x11, 0xCC, 0x49, 0x02, 0xD0, 0xC0, 0x33, 0xA6, 0x3F, 0x23, 0x6A, 0x71, 0xDA, 0x97, 0x4A, 0x6F, 0x40, 0x4F, 0x7A, 0xA7, 0xB5, 0xE5, 0x82, + 0xC7, 0x58, 0x14, 0x2F, 0xC1, 0x82, 0x6B, 0xBA, 0x98, 0xB2, 0x7D, 0x57, 0xC2, 0xE2, 0x10, 0x3E, 0x10, 0xE3, 0x0D, 0x32, 0x79, 0x7B, 0x96, 0x77, 0x14, 0xD1, 0x56, 0x61, 0x11, 0x13, 0x71, 0xA2, + 0xD9, 0xC5, 0x39, 0x98, 0x12, 0x46, 0x46, 0x22, 0x63, 0x5B, 0x44, 0x21, 0x26, 0xB0, 0x98, 0x36, 0xB0, 0x81, 0x82, 0x72, 0x47, 0xD0, 0x54, 0x22, 0x97, 0x2B, 0xD0, 0x32, 0x0D, 0x8F, 0x42, 0xBF, + 0x57, 0xE3, 0x49, 0x46, 0x12, 0x34, 0xE4, 0xD9, 0x4F, 0x01, 0x18, 0x50, 0xBA, 0xB5, 0xC0, 0x49, 0xB6, 0x2A, 0x59, 0x43, 0x38, 0x66, 0xFC, 0xCE, 0x69, 0x66, 0x49, 0x5C, 0x26, 0x5C, 0x47, 0x65, + 0xA5, 0x6C, 0x06, 0xB9, 0xFC, 0x42, 0x76, 0x54, 0x87, 0x85, 0xF4, 0x68, 0x28, 0xCA, 0x60, 0x2D, 0xC6, 0xD0, 0x54, 0x1F, 0x25, 0x07, 0x89, 0xC4, 0x9E, 0x8B, 0x06, 0x55, 0x9C, 0x43, 0x44, 0x60, + 0xA8, 0x43, 0x80, 0x98, 0x54, 0xE5, 0xB4, 0x6E, 0x89, 0x38, 0x9F, 0x10, 0xF4, 0x89, 0x66, 0x74, 0x91, 0xC1, 0x93, 0x5E, 0x8A, 0xFB, 0x9E, 0xB4, 0x71, 0x8F, 0x86, 0xAC, 0x45, 0x89, 0x32, 0xBC, + 0xF3, 0x3C, 0x9A, 0xBE, 0xCB, 0x2D, 0xC0, 0xC0, 0x93, 0xA7, 0xE8, 0x1D, 0xA0, 0x32, 0x7B, 0xB6, 0x37, 0x52, 0x81, 0x05, 0xC3, 0x58, 0xEB, 0x76, 0x8D, 0x32, 0x3A, 0x37, 0xD4, 0x0A, 0x8C, 0x19, + 0x9B, 0x7C, 0x4B, 0xB1, 0xD7, 0x2B, 0x72, 0xB6, 0x90, 0xB3, 0x6D, 0xD2, 0x7A, 0x93, 0x55, 0x19, 0x1B, 0x3C, 0x3A, 0xA6, 0x75, 0xA7, 0xE6, 0xF8, 0x55, 0xEB, 0x50, 0x5F, 0x57, 0x98, 0x65, 0xDB, + 0xD8, 0x91, 0x05, 0x65, 0x50, 0x5E, 0x7C, 0x0F, 0xDD, 0x54, 0x5C, 0xBB, 0xB8, 0x71, 0xB0, 0xB2, 0xCC, 0x01, 0x25, 0xB7, 0x4F, 0x6B, 0x0C, 0x9B, 0x79, 0x67, 0x0A, 0x62, 0x02, 0xD1, 0xB9, 0x15, + 0x4A, 0xC7, 0x76, 0x6B, 0x19, 0x19, 0xC4, 0x89, 0x58, 0x90, 0x86, 0xAD, 0x8B, 0x45, 0xBE, 0x0D, 0x79, 0xC9, 0x76, 0xC3, 0xC3, 0x9D, 0x6B, 0x25, 0x21, 0x3B, 0xB0, 0xB7, 0x8A, 0x57, 0x50, 0xE6, + 0xA8, 0xEB, 0x34, 0x33, 0x0B, 0xB3, 0xCF, 0xF2, 0xB1, 0xC0, 0x72, 0x2A, 0xC8, 0x83, 0xB0, 0x48, 0xF4, 0xB8, 0xCD, 0x06, 0x19, 0x6D, 0xA8, 0xAA, 0x8B, 0x05, 0xDA, 0x42, 0x67, 0x55, 0x2B, 0xF8, + 0x7A, 0xBC, 0xA5, 0x12, 0x4D, 0xC3, 0x58, 0xA8, 0x38, 0x10, 0x40, 0xE9, 0xB8, 0x1F, 0xB0, 0x84, 0x43, 0x15, 0x02, 0x15, 0xD6, 0x92, 0x23, 0x28, 0x00, 0x0A, 0xC0, 0xB7, 0x88, 0xB1, 0x21, 0x93, + 0x1A, 0x26, 0x7D, 0x80, 0x61, 0x9C, 0xE7, 0xD2, 0x9C, 0xD7, 0x6B, 0x60, 0xCF, 0x65, 0x83, 0xDC, 0xE8, 0xCE, 0xBC, 0x49, 0x01, 0x85, 0x73, 0x6C, 0x81, 0x8B, 0x25, 0xAD, 0x26, 0x0B, 0x66, 0x7B, + 0x1F, 0xFD, 0x46, 0x20, 0x6D, 0x01, 0x04, 0x55, 0x3A, 0xA9, 0xFB, 0x30, 0x45, 0x54, 0xA2, 0x1C, 0x32, 0x72, 0x44, 0xCE, 0x78, 0xAF, 0xDB, 0xD3, 0xB4, 0x62, 0x36, 0x1B, 0xB0, 0x68, 0xA1, 0x55, + 0x63, 0x64, 0x09, 0xF5, 0x74, 0xC5, 0x71, 0x65, 0x72, 0xE2, 0xA5, 0xF2, 0xA4, 0xB0, 0x4F, 0xB8, 0xAA, 0xD1, 0x23, 0x66, 0x84, 0x84, 0x17, 0x87, 0x56, 0x2A, 0xAF, 0x46, 0xC2, 0xC0, 0xDA, 0x46, + 0x65, 0xEA, 0xFD, 0x46, 0x5F, 0xC6, 0x4A, 0x0C, 0x5F, 0x8F, 0x3F, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9D, 0x59, 0xA5, 0x43, 0xD8, 0x20, 0x8C, 0x54, 0xA3, 0x16, 0x65, 0x29, 0xB5, 0x39, 0x22, + 0xA5, 0x89, 0x9A, 0x0B, 0xC4, 0x65, 0xEE, 0x5F, 0xC2, 0xC0, 0x41, 0x55, 0x58, 0x2A, 0x40, 0xAC, 0x70, 0x97, 0x61, 0xD2, 0xBE, 0x61, 0xFD, 0xC7, 0x6C, 0x59, 0x30, 0x44, 0xCE, 0xBC, 0xC7, 0xF2, + 0x86, 0x26, 0xED, 0x79, 0xD4, 0x51, 0x14, 0x08, 0x00, 0xE0, 0x3B, 0x59, 0xB9, 0x56, 0xF8, 0x21, 0x0E, 0x55, 0x60, 0x67, 0x40, 0x7D, 0x13, 0xDC, 0x90, 0xFA, 0x9E, 0x8B, 0x87, 0x2B, 0xFB, 0x8F, + }, + .pk_len = 1568, + .pk = { + 0xDA, 0x18, 0x71, 0x2D, 0x31, 0x6E, 0x98, 0xDC, 0x7A, 0xC8, 0xC3, 0xCA, 0x47, 0x37, 0x0E, 0xBD, 0x77, 0x0C, 0xE3, 0x2B, 0x3B, 0xD4, 0xB1, 0xA0, 0xC9, 0x52, 0x9A, 0xC6, 0xEC, 0x8E, 0xE0, 0x28, + 0xB1, 0xCD, 0xB2, 0x65, 0x1C, 0xB5, 0xA6, 0xBB, 0x3C, 0x0C, 0x6D, 0xF1, 0x24, 0x0A, 0x3B, 0x91, 0x4B, 0x56, 0x56, 0xC0, 0xDC, 0x51, 0xC2, 0xB9, 0x1B, 0xFC, 0xBC, 0x37, 0xA4, 0x66, 0x02, 0x87, + 0xD4, 0x4F, 0x81, 0xF8, 0x53, 0xC7, 0xF4, 0x9A, 0x6D, 0x06, 0x03, 0xD6, 0xD7, 0x23, 0xCB, 0xEC, 0x01, 0x5F, 0xBC, 0x43, 0x4A, 0x38, 0x24, 0x1C, 0x10, 0x9C, 0x7E, 0xD5, 0xB1, 0xCC, 0x46, 0x1A, + 0x2C, 0xCB, 0x9A, 0xB7, 0x14, 0x0F, 0x19, 0xF3, 0x7A, 0x13, 0xBB, 0x70, 0x1E, 0x14, 0x2B, 0xD5, 0x4B, 0x64, 0xEC, 0x6B, 0x76, 0xFE, 0xC3, 0x3B, 0x69, 0xC2, 0x91, 0x8C, 0xB0, 0x17, 0xC4, 0x14, + 0x34, 0x23, 0x00, 0x9A, 0x3C, 0x07, 0xB5, 0xC1, 0x81, 0xB0, 0xC1, 0xEB, 0x49, 0x4A, 0x62, 0xAB, 0xC8, 0x39, 0x13, 0x97, 0x08, 0x9E, 0xA6, 0x64, 0x09, 0x67, 0xC1, 0x20, 0x49, 0x84, 0xCD, 0x48, + 0x4C, 0xCC, 0xB0, 0x0A, 0x9A, 0x17, 0xD0, 0x87, 0x21, 0x84, 0x28, 0xEF, 0x3B, 0xB7, 0x08, 0x78, 0x3E, 0x12, 0x82, 0x71, 0x04, 0x41, 0x73, 0x75, 0xB6, 0x95, 0x6F, 0xB5, 0x00, 0x53, 0xD0, 0x48, + 0xA4, 0x79, 0x14, 0x95, 0x82, 0x4A, 0x34, 0x80, 0xA5, 0xB7, 0x83, 0x02, 0x56, 0x09, 0x6F, 0xDD, 0x72, 0x5C, 0x30, 0x8B, 0x3B, 0xE8, 0x4A, 0x07, 0xF3, 0x63, 0x2E, 0x24, 0x95, 0xC6, 0x2E, 0x96, + 0x39, 0x9D, 0x80, 0xBF, 0xA7, 0x45, 0xB9, 0x84, 0x1A, 0x18, 0x33, 0xBC, 0x1D, 0x27, 0xBA, 0x45, 0xA5, 0x21, 0x68, 0xEE, 0x59, 0x00, 0x6C, 0x3A, 0x3A, 0x8C, 0x4A, 0x5A, 0x4F, 0x50, 0x88, 0xFC, + 0x73, 0x71, 0x81, 0xAB, 0x51, 0x96, 0xF7, 0xB1, 0xB4, 0x9A, 0x2E, 0xD8, 0x13, 0x13, 0x4E, 0x11, 0x2F, 0x73, 0x0B, 0x99, 0x1C, 0x54, 0xA7, 0x19, 0x6B, 0xCF, 0x5F, 0xC7, 0x6E, 0x13, 0x4C, 0x58, + 0x43, 0xE1, 0x69, 0x88, 0x51, 0xB2, 0xF8, 0x69, 0xAF, 0xAF, 0xB0, 0x27, 0x87, 0xD9, 0xC2, 0xF1, 0x36, 0x90, 0x2D, 0xC7, 0xA7, 0xF3, 0xD6, 0x21, 0x56, 0xD1, 0x5E, 0xC3, 0x09, 0x56, 0x40, 0x92, + 0xC6, 0x1D, 0x83, 0xB0, 0x98, 0x6C, 0x48, 0x40, 0x99, 0x81, 0xF3, 0xC1, 0x86, 0x88, 0x0A, 0x2F, 0x63, 0xD5, 0x86, 0x0A, 0xB6, 0x01, 0xDE, 0xAC, 0x2B, 0x6B, 0xA1, 0xB4, 0x28, 0x17, 0x9D, 0x73, + 0x53, 0x3E, 0xB7, 0xA3, 0xA5, 0x11, 0x3B, 0x85, 0x61, 0xF1, 0x0B, 0x45, 0xC3, 0xCD, 0xE2, 0x82, 0xB6, 0xEA, 0xD6, 0xAB, 0x6C, 0x60, 0x4F, 0x09, 0xC1, 0x7B, 0xFD, 0xA0, 0x83, 0x13, 0xA3, 0x26, + 0x07, 0x67, 0x5A, 0xDF, 0x64, 0x31, 0xCA, 0x87, 0x18, 0xE9, 0xC4, 0x3A, 0x73, 0x73, 0x32, 0x27, 0xE7, 0x3B, 0xC6, 0x1A, 0xC8, 0x45, 0xBA, 0x90, 0x77, 0x55, 0xCE, 0xC6, 0x89, 0x25, 0xE5, 0xE2, + 0xBF, 0xE9, 0x12, 0x95, 0x9D, 0xB8, 0x6F, 0xBF, 0xE2, 0x15, 0x6F, 0xD5, 0xBB, 0xDB, 0xF0, 0xC9, 0xDF, 0x8B, 0x53, 0x02, 0xAA, 0x8D, 0x90, 0xA2, 0x2D, 0x12, 0x27, 0x0E, 0x00, 0x65, 0x51, 0xE4, + 0x76, 0x7E, 0x45, 0x26, 0x8E, 0xD9, 0x69, 0x26, 0x54, 0x44, 0x78, 0x11, 0xEA, 0xB8, 0x4F, 0x04, 0x99, 0xA8, 0xA5, 0x8C, 0xF7, 0xC0, 0x4A, 0x59, 0x56, 0x98, 0x52, 0x80, 0x45, 0xF2, 0x98, 0x97, + 0xC8, 0xFA, 0x96, 0xD0, 0x6C, 0xCE, 0x51, 0xE6, 0xAF, 0xEA, 0xC4, 0x33, 0x95, 0x89, 0xC9, 0x41, 0xC8, 0x55, 0x63, 0xD7, 0x0F, 0xAC, 0xE1, 0x92, 0x88, 0x94, 0xBA, 0xC0, 0x36, 0x19, 0xDF, 0xF4, + 0xBE, 0x3F, 0x43, 0x14, 0xA3, 0xF7, 0x35, 0x1A, 0x09, 0xA4, 0x86, 0xB5, 0x04, 0x1E, 0x7C, 0xB2, 0xDA, 0x8B, 0x96, 0xBC, 0x66, 0x26, 0xA4, 0x93, 0x17, 0x35, 0x7C, 0x41, 0x52, 0xA5, 0x1B, 0xA3, + 0xC2, 0x8C, 0x7E, 0x0C, 0x9D, 0xB4, 0x1A, 0x06, 0xA2, 0x82, 0x90, 0xF2, 0x18, 0x73, 0x11, 0x07, 0xC9, 0x54, 0xD8, 0xA6, 0x6F, 0x80, 0x1D, 0x7D, 0xE1, 0x2A, 0x03, 0x71, 0x16, 0x99, 0x0B, 0x6C, + 0x53, 0xC1, 0x29, 0xF1, 0x85, 0xC3, 0x45, 0xF2, 0x7E, 0x51, 0x8B, 0x2D, 0x5A, 0x91, 0x25, 0xA0, 0x70, 0x76, 0xD9, 0x91, 0xB7, 0xDA, 0xC7, 0xCC, 0x65, 0xA8, 0x56, 0x2E, 0xFB, 0xCC, 0x32, 0xA9, + 0xCA, 0x4A, 0xD9, 0x02, 0x63, 0xB0, 0x4A, 0x4F, 0x90, 0x36, 0x11, 0x6C, 0x7B, 0x97, 0x48, 0x04, 0x96, 0x31, 0x75, 0x75, 0x65, 0x0D, 0xCC, 0x21, 0x52, 0xB5, 0xBC, 0x0E, 0x74, 0x40, 0x7E, 0x12, + 0xFA, 0x8E, 0x4F, 0xFC, 0xCC, 0xFF, 0x76, 0xC0, 0x1A, 0x97, 0x4B, 0xD6, 0x11, 0x02, 0xE1, 0xF5, 0x29, 0x64, 0x96, 0xC7, 0x1D, 0x07, 0x64, 0xE1, 0x32, 0x29, 0xFF, 0xE7, 0x84, 0x6F, 0x33, 0x6E, + 0x34, 0xCA, 0xC9, 0x04, 0xCA, 0x56, 0x70, 0xF8, 0xCD, 0x50, 0x52, 0x42, 0x7A, 0x79, 0xC0, 0x91, 0xA9, 0x71, 0x21, 0x0C, 0x5C, 0xFF, 0x66, 0x7A, 0xAC, 0x24, 0x93, 0x66, 0xE1, 0x0D, 0x2B, 0x11, + 0x37, 0x6C, 0xA3, 0x9D, 0x93, 0x52, 0x04, 0xB1, 0x2C, 0xC5, 0x85, 0xE9, 0x40, 0x54, 0x03, 0x62, 0x5F, 0xB3, 0x2C, 0xB5, 0xE5, 0xC3, 0x1B, 0x62, 0x34, 0x81, 0x60, 0x51, 0x5C, 0xCC, 0x4F, 0xDA, + 0xF5, 0x70, 0x2D, 0x6B, 0xAB, 0x5C, 0x37, 0x3D, 0xB6, 0xF3, 0x50, 0xD3, 0xE6, 0x3A, 0x5C, 0xE3, 0xCA, 0x54, 0x74, 0xA0, 0xCF, 0x15, 0x67, 0x04, 0x2C, 0xA3, 0x25, 0x89, 0x86, 0xFF, 0x75, 0xBD, + 0xFC, 0xD9, 0x29, 0xE6, 0x46, 0x2F, 0x36, 0xBC, 0xCC, 0x3F, 0x5A, 0x93, 0x35, 0x2A, 0x2B, 0x36, 0xCB, 0x16, 0x2E, 0x18, 0x74, 0xC7, 0x42, 0x87, 0x0A, 0x97, 0xB1, 0x67, 0xA0, 0x50, 0x37, 0x36, + 0x24, 0xEA, 0xEB, 0x7E, 0x50, 0x73, 0x25, 0x6B, 0x72, 0x11, 0xB2, 0xD9, 0x4B, 0x84, 0x06, 0xCD, 0x6C, 0x95, 0x33, 0xB1, 0x53, 0x64, 0x08, 0xAB, 0x0A, 0x29, 0xE5, 0xB2, 0xF0, 0xC9, 0x54, 0xEC, + 0xE0, 0x0F, 0xBB, 0xEB, 0x17, 0x6D, 0x72, 0x4D, 0x4C, 0xF4, 0x43, 0xCF, 0x70, 0x20, 0xD5, 0xFA, 0x70, 0x94, 0xCC, 0x1B, 0x1B, 0xE6, 0x97, 0xBA, 0xD3, 0x36, 0x74, 0xE4, 0x09, 0x9E, 0xC7, 0xBB, + 0x18, 0xF4, 0x57, 0x71, 0x28, 0xCD, 0xD9, 0x7C, 0xCD, 0x6D, 0x44, 0x62, 0xE5, 0x60, 0x7C, 0x51, 0x2A, 0x3E, 0x36, 0x24, 0x8E, 0x3D, 0xDA, 0xA2, 0xEC, 0x08, 0x9A, 0xEF, 0xC4, 0xCE, 0x48, 0x5C, + 0x49, 0xD7, 0xB0, 0x09, 0xC8, 0xD6, 0x31, 0x15, 0xFC, 0x81, 0xFF, 0x3A, 0x62, 0xD1, 0x5A, 0x88, 0x44, 0x1C, 0x03, 0xEA, 0x1C, 0x2E, 0x72, 0xC4, 0x88, 0x39, 0xFC, 0x6A, 0xD7, 0x3A, 0x30, 0x74, + 0x4A, 0x62, 0xB7, 0xB2, 0x16, 0x45, 0xA6, 0xAF, 0x7D, 0x61, 0xB6, 0x38, 0x3B, 0x22, 0x1E, 0x21, 0x90, 0x55, 0x57, 0xCD, 0x29, 0xD9, 0x24, 0xA6, 0x09, 0x86, 0xC5, 0x11, 0xC1, 0xEB, 0xBC, 0x31, + 0x6D, 0x56, 0x30, 0xA2, 0x41, 0x43, 0x23, 0xF5, 0x3A, 0xD5, 0x59, 0x94, 0xF6, 0xB3, 0x65, 0x39, 0xF9, 0xC4, 0x40, 0x75, 0xA5, 0x33, 0xE4, 0x81, 0xC0, 0x84, 0x45, 0xD9, 0xCA, 0x9E, 0x9D, 0x38, + 0x21, 0x19, 0x38, 0x8B, 0xD1, 0xD7, 0x50, 0x52, 0x21, 0x7A, 0x94, 0x4C, 0xCC, 0x7B, 0xE9, 0x09, 0xE2, 0x19, 0x71, 0x1F, 0xCC, 0x79, 0x24, 0x76, 0x92, 0x13, 0xA1, 0x92, 0x53, 0x4A, 0x55, 0x80, + 0x08, 0x15, 0x7A, 0x39, 0x6E, 0xDF, 0xF4, 0x80, 0xCC, 0x3B, 0x52, 0x0F, 0xF8, 0x18, 0xB3, 0x8B, 0x13, 0x5C, 0x18, 0xA8, 0x0D, 0x51, 0x05, 0xE6, 0x78, 0x83, 0x6C, 0x39, 0x5C, 0x28, 0xE9, 0x2F, + 0x7A, 0x3C, 0x4E, 0x93, 0xC0, 0x10, 0x35, 0xF3, 0x41, 0x11, 0xCC, 0x49, 0x02, 0xD0, 0xC0, 0x33, 0xA6, 0x3F, 0x23, 0x6A, 0x71, 0xDA, 0x97, 0x4A, 0x6F, 0x40, 0x4F, 0x7A, 0xA7, 0xB5, 0xE5, 0x82, + 0xC7, 0x58, 0x14, 0x2F, 0xC1, 0x82, 0x6B, 0xBA, 0x98, 0xB2, 0x7D, 0x57, 0xC2, 0xE2, 0x10, 0x3E, 0x10, 0xE3, 0x0D, 0x32, 0x79, 0x7B, 0x96, 0x77, 0x14, 0xD1, 0x56, 0x61, 0x11, 0x13, 0x71, 0xA2, + 0xD9, 0xC5, 0x39, 0x98, 0x12, 0x46, 0x46, 0x22, 0x63, 0x5B, 0x44, 0x21, 0x26, 0xB0, 0x98, 0x36, 0xB0, 0x81, 0x82, 0x72, 0x47, 0xD0, 0x54, 0x22, 0x97, 0x2B, 0xD0, 0x32, 0x0D, 0x8F, 0x42, 0xBF, + 0x57, 0xE3, 0x49, 0x46, 0x12, 0x34, 0xE4, 0xD9, 0x4F, 0x01, 0x18, 0x50, 0xBA, 0xB5, 0xC0, 0x49, 0xB6, 0x2A, 0x59, 0x43, 0x38, 0x66, 0xFC, 0xCE, 0x69, 0x66, 0x49, 0x5C, 0x26, 0x5C, 0x47, 0x65, + 0xA5, 0x6C, 0x06, 0xB9, 0xFC, 0x42, 0x76, 0x54, 0x87, 0x85, 0xF4, 0x68, 0x28, 0xCA, 0x60, 0x2D, 0xC6, 0xD0, 0x54, 0x1F, 0x25, 0x07, 0x89, 0xC4, 0x9E, 0x8B, 0x06, 0x55, 0x9C, 0x43, 0x44, 0x60, + 0xA8, 0x43, 0x80, 0x98, 0x54, 0xE5, 0xB4, 0x6E, 0x89, 0x38, 0x9F, 0x10, 0xF4, 0x89, 0x66, 0x74, 0x91, 0xC1, 0x93, 0x5E, 0x8A, 0xFB, 0x9E, 0xB4, 0x71, 0x8F, 0x86, 0xAC, 0x45, 0x89, 0x32, 0xBC, + 0xF3, 0x3C, 0x9A, 0xBE, 0xCB, 0x2D, 0xC0, 0xC0, 0x93, 0xA7, 0xE8, 0x1D, 0xA0, 0x32, 0x7B, 0xB6, 0x37, 0x52, 0x81, 0x05, 0xC3, 0x58, 0xEB, 0x76, 0x8D, 0x32, 0x3A, 0x37, 0xD4, 0x0A, 0x8C, 0x19, + 0x9B, 0x7C, 0x4B, 0xB1, 0xD7, 0x2B, 0x72, 0xB6, 0x90, 0xB3, 0x6D, 0xD2, 0x7A, 0x93, 0x55, 0x19, 0x1B, 0x3C, 0x3A, 0xA6, 0x75, 0xA7, 0xE6, 0xF8, 0x55, 0xEB, 0x50, 0x5F, 0x57, 0x98, 0x65, 0xDB, + 0xD8, 0x91, 0x05, 0x65, 0x50, 0x5E, 0x7C, 0x0F, 0xDD, 0x54, 0x5C, 0xBB, 0xB8, 0x71, 0xB0, 0xB2, 0xCC, 0x01, 0x25, 0xB7, 0x4F, 0x6B, 0x0C, 0x9B, 0x79, 0x67, 0x0A, 0x62, 0x02, 0xD1, 0xB9, 0x15, + 0x4A, 0xC7, 0x76, 0x6B, 0x19, 0x19, 0xC4, 0x89, 0x58, 0x90, 0x86, 0xAD, 0x8B, 0x45, 0xBE, 0x0D, 0x79, 0xC9, 0x76, 0xC3, 0xC3, 0x9D, 0x6B, 0x25, 0x21, 0x3B, 0xB0, 0xB7, 0x8A, 0x57, 0x50, 0xE6, + 0xA8, 0xEB, 0x34, 0x33, 0x0B, 0xB3, 0xCF, 0xF2, 0xB1, 0xC0, 0x72, 0x2A, 0xC8, 0x83, 0xB0, 0x48, 0xF4, 0xB8, 0xCD, 0x06, 0x19, 0x6D, 0xA8, 0xAA, 0x8B, 0x05, 0xDA, 0x42, 0x67, 0x55, 0x2B, 0xF8, + 0x7A, 0xBC, 0xA5, 0x12, 0x4D, 0xC3, 0x58, 0xA8, 0x38, 0x10, 0x40, 0xE9, 0xB8, 0x1F, 0xB0, 0x84, 0x43, 0x15, 0x02, 0x15, 0xD6, 0x92, 0x23, 0x28, 0x00, 0x0A, 0xC0, 0xB7, 0x88, 0xB1, 0x21, 0x93, + 0x1A, 0x26, 0x7D, 0x80, 0x61, 0x9C, 0xE7, 0xD2, 0x9C, 0xD7, 0x6B, 0x60, 0xCF, 0x65, 0x83, 0xDC, 0xE8, 0xCE, 0xBC, 0x49, 0x01, 0x85, 0x73, 0x6C, 0x81, 0x8B, 0x25, 0xAD, 0x26, 0x0B, 0x66, 0x7B, + 0x1F, 0xFD, 0x46, 0x20, 0x6D, 0x01, 0x04, 0x55, 0x3A, 0xA9, 0xFB, 0x30, 0x45, 0x54, 0xA2, 0x1C, 0x32, 0x72, 0x44, 0xCE, 0x78, 0xAF, 0xDB, 0xD3, 0xB4, 0x62, 0x36, 0x1B, 0xB0, 0x68, 0xA1, 0x55, + 0x63, 0x64, 0x09, 0xF5, 0x74, 0xC5, 0x71, 0x65, 0x72, 0xE2, 0xA5, 0xF2, 0xA4, 0xB0, 0x4F, 0xB8, 0xAA, 0xD1, 0x23, 0x66, 0x84, 0x84, 0x17, 0x87, 0x56, 0x2A, 0xAF, 0x46, 0xC2, 0xC0, 0xDA, 0x46, + 0x65, 0xEA, 0xFD, 0x46, 0x5F, 0xC6, 0x4A, 0x0C, 0x5F, 0x8F, 0x3F, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9D, 0x59, 0xA5, 0x43, 0xD8, 0x20, 0x8C, 0x54, 0xA3, 0x16, 0x65, 0x29, 0xB5, 0x39, 0x22, + }, + .pkcs8_len = 0, + .spki_len = 0, + .secret_len = 32, + .secret = { + 0xfb, 0xc4, 0xee, 0xa6, 0x91, 0xee, 0xf4, 0xc1, 0xb4, 0x76, 0xa2, 0x99, 0x36, 0x45, 0x3f, 0x4c, 0x3d, 0x48, 0x81, 0x79, 0x4e, 0xe3, 0x7b, 0xaf, 0x0f, 0xd7, 0x28, 0x40, 0x74, 0x3e, 0x7b, 0x7d, + }, + .cipher_len = 1568, + .cipher = { + 0xc2, 0x7f, 0x01, 0x24, 0x4d, 0x4b, 0x3f, 0xb2, 0x1d, 0x84, 0x37, 0xf8, 0x40, 0x01, 0x7c, 0xcc, 0xb7, 0xb7, 0xda, 0xd5, 0xfb, 0x2b, 0x47, 0xb9, 0xb5, 0x7e, 0xae, 0x4f, 0x77, 0xd0, 0xa4, 0x55, + 0x5e, 0x50, 0x92, 0xa2, 0x49, 0x69, 0xf2, 0x27, 0x3e, 0x97, 0x02, 0x88, 0x4a, 0x08, 0x47, 0x7b, 0x56, 0x8d, 0x80, 0x17, 0xf1, 0x38, 0x75, 0xd1, 0xf5, 0xa6, 0xd4, 0x13, 0xbd, 0xd2, 0x28, 0xeb, + 0xb1, 0x12, 0x60, 0xf7, 0xf4, 0x52, 0x9c, 0xbc, 0xeb, 0xf9, 0xb6, 0x86, 0x2e, 0x8a, 0x84, 0x12, 0x35, 0xf2, 0x9f, 0x60, 0xf8, 0xe8, 0x41, 0x74, 0x34, 0x18, 0x9d, 0x57, 0x99, 0x20, 0xfe, 0x6b, + 0x98, 0xdb, 0xe7, 0x13, 0xec, 0x16, 0xc3, 0xfd, 0xdb, 0xb8, 0x1e, 0x73, 0x1d, 0x95, 0x6b, 0x06, 0xdb, 0x49, 0x80, 0xf4, 0x9c, 0x26, 0xf2, 0x86, 0x61, 0xff, 0x9c, 0xe6, 0xe9, 0xd8, 0x61, 0xec, + 0x7a, 0x09, 0x84, 0x0c, 0x19, 0xde, 0x0e, 0xb6, 0x72, 0x20, 0x71, 0xf8, 0xaa, 0x48, 0x36, 0x2d, 0x2f, 0xf1, 0x27, 0xa4, 0xae, 0x46, 0xf9, 0x93, 0x37, 0x82, 0x68, 0x32, 0xad, 0xac, 0x23, 0x91, + 0x65, 0xf2, 0x25, 0x85, 0xbb, 0x57, 0xa8, 0x89, 0xc9, 0xc6, 0xaf, 0x82, 0x36, 0x7e, 0xc7, 0xb0, 0x72, 0x37, 0xc0, 0x53, 0x5b, 0x31, 0xb3, 0x8c, 0x1c, 0xac, 0x40, 0xac, 0x1a, 0x0c, 0x95, 0x8a, + 0x18, 0x87, 0xfe, 0x34, 0x71, 0x10, 0x83, 0xfd, 0x37, 0xaf, 0x4b, 0xc5, 0xb1, 0xb4, 0xe1, 0xe2, 0xee, 0x28, 0x43, 0x69, 0x3d, 0x57, 0xdd, 0x1e, 0x65, 0x7d, 0x4c, 0x24, 0xed, 0x20, 0x7e, 0xe7, + 0x12, 0xad, 0x2a, 0x08, 0x91, 0x45, 0x81, 0x80, 0xe9, 0xe8, 0xbd, 0x36, 0xfc, 0x14, 0xd8, 0xd6, 0x33, 0xf5, 0xb7, 0x41, 0xce, 0xa1, 0x08, 0xd2, 0xd4, 0xfd, 0x75, 0x1c, 0x5a, 0x67, 0xb0, 0x5e, + 0x30, 0x32, 0x4a, 0x67, 0xe9, 0xdd, 0x75, 0xc9, 0x93, 0xd4, 0xfe, 0x08, 0x54, 0xfb, 0x78, 0xdf, 0x6f, 0x3d, 0x45, 0xa2, 0xa9, 0xc8, 0xe4, 0x25, 0x10, 0xf0, 0xc3, 0xd8, 0x02, 0x03, 0x71, 0x2f, + 0xb3, 0x9e, 0x36, 0xb5, 0xdd, 0x8b, 0x5c, 0xcd, 0x3d, 0x09, 0xce, 0xa9, 0x42, 0x03, 0xba, 0xf8, 0x72, 0x08, 0x45, 0x71, 0xec, 0xf9, 0x78, 0xbd, 0xb9, 0x54, 0x8a, 0x25, 0x0e, 0xe4, 0x90, 0x7b, + 0x4a, 0xfc, 0x31, 0xb2, 0x1f, 0x31, 0x9a, 0xe4, 0xbf, 0x0a, 0xb1, 0x9c, 0xbd, 0x11, 0xeb, 0xe1, 0x33, 0x59, 0xd1, 0xaa, 0xf4, 0xfd, 0xb8, 0x3b, 0x65, 0x02, 0x50, 0x14, 0x22, 0xa5, 0xfe, 0x50, + 0xa8, 0xa3, 0x8e, 0xf5, 0x3d, 0xeb, 0x60, 0x3c, 0xe2, 0x3f, 0xd9, 0x79, 0x2b, 0x04, 0xde, 0xb3, 0x78, 0x71, 0x9a, 0xb7, 0x69, 0xaa, 0x58, 0x97, 0xcc, 0x65, 0xe9, 0xb1, 0x63, 0x04, 0xce, 0xa5, + 0x37, 0xe1, 0x76, 0x2b, 0xd8, 0xc9, 0xb1, 0x09, 0xda, 0x14, 0xa8, 0x29, 0xe6, 0x41, 0x9f, 0x1b, 0x9f, 0xf8, 0xa4, 0x66, 0xe2, 0xa6, 0xd6, 0xb3, 0x4d, 0x74, 0xff, 0xe1, 0xa5, 0x92, 0x99, 0x18, + 0x17, 0x59, 0xd0, 0xd3, 0x87, 0xfc, 0xed, 0x1d, 0x90, 0x7f, 0x5f, 0xb5, 0xed, 0xb4, 0x26, 0xc0, 0x51, 0x30, 0xe6, 0xca, 0x59, 0x09, 0xb2, 0x76, 0xd1, 0xa4, 0x7e, 0x71, 0x3c, 0x30, 0xd9, 0x96, + 0xda, 0x5e, 0x8e, 0x57, 0xe7, 0x12, 0xc7, 0x77, 0x38, 0xf2, 0x1b, 0xe7, 0x4b, 0x42, 0xb5, 0x18, 0x43, 0x2d, 0xad, 0x7e, 0xf7, 0x3e, 0x6a, 0x8c, 0x43, 0xaa, 0x9a, 0x62, 0x69, 0x94, 0xd7, 0x1a, + 0x31, 0x81, 0x28, 0x51, 0x80, 0x6e, 0x9f, 0xbb, 0x1f, 0x2b, 0xd3, 0x56, 0xce, 0xa3, 0x9d, 0x95, 0xf2, 0xf8, 0x7c, 0xa3, 0x0d, 0xaf, 0x6f, 0x27, 0x33, 0xf7, 0xbc, 0xe7, 0x9f, 0x8d, 0xa9, 0x95, + 0x05, 0x1e, 0x49, 0xa7, 0xfd, 0x22, 0x64, 0x37, 0x9c, 0x0a, 0x75, 0x2e, 0x55, 0x3e, 0xd6, 0x08, 0xeb, 0x93, 0x44, 0xc7, 0x94, 0x98, 0xf6, 0x91, 0x53, 0x85, 0x64, 0xc5, 0x4f, 0x82, 0x3b, 0xb7, + 0x0b, 0x12, 0xb5, 0x9e, 0x88, 0x24, 0xb4, 0xa4, 0xbb, 0x1e, 0xea, 0xc6, 0x7c, 0x81, 0x0c, 0xcc, 0x2e, 0x23, 0x74, 0x47, 0x83, 0xce, 0x95, 0x80, 0x97, 0xf7, 0xa6, 0xbc, 0x6e, 0x1f, 0x17, 0x59, + 0x75, 0x21, 0xb8, 0xc3, 0xd1, 0xee, 0x85, 0x96, 0xa2, 0x9f, 0xfe, 0xf1, 0x4e, 0xd9, 0x16, 0x32, 0x09, 0x7c, 0x16, 0xd5, 0x06, 0x5d, 0xb2, 0xa9, 0x63, 0xca, 0x73, 0x83, 0xac, 0x60, 0xad, 0x8f, + 0x4e, 0xd0, 0xd4, 0x1b, 0xd0, 0xbc, 0x3b, 0xaf, 0x19, 0x8c, 0x51, 0x25, 0xae, 0x91, 0x15, 0x06, 0xc9, 0x26, 0xd4, 0xc1, 0x17, 0x85, 0xfd, 0x61, 0x82, 0x29, 0xbf, 0xf5, 0x4c, 0xb1, 0x16, 0x1a, + 0xb8, 0xfc, 0x7b, 0x51, 0xda, 0xec, 0xcc, 0xd9, 0x13, 0x1e, 0xdf, 0x43, 0x7d, 0x8e, 0x52, 0x8e, 0x75, 0x81, 0xb8, 0x2c, 0x66, 0x0e, 0x8c, 0x5e, 0x25, 0x12, 0xd5, 0xf6, 0x38, 0x0a, 0x52, 0x8f, + 0x2a, 0xe4, 0xae, 0xe2, 0x63, 0xdb, 0x96, 0x76, 0x02, 0x4b, 0xc7, 0xad, 0x39, 0x8b, 0xc9, 0xcd, 0xda, 0xd6, 0x07, 0x96, 0x8b, 0xba, 0xb2, 0x23, 0x29, 0xe0, 0x4d, 0x6e, 0x77, 0x1f, 0xe6, 0x47, + 0x10, 0x7a, 0xc4, 0x66, 0x67, 0xa5, 0x1a, 0xd5, 0x58, 0xa6, 0x35, 0xf0, 0x26, 0x95, 0x1f, 0x4f, 0x48, 0xc8, 0x88, 0xd7, 0x01, 0xc2, 0xaf, 0xf4, 0xea, 0xb4, 0xe3, 0x4a, 0xdb, 0x15, 0x9a, 0xbb, + 0xbf, 0xab, 0xe5, 0x9b, 0x3f, 0x4c, 0xf8, 0xaa, 0xb1, 0xdd, 0x66, 0x1e, 0x4d, 0xd0, 0xc5, 0x55, 0x8d, 0xc0, 0x59, 0x20, 0x2e, 0xe6, 0x46, 0x25, 0xa3, 0xb4, 0xb9, 0x2f, 0xf4, 0xd1, 0x56, 0x97, + 0xf1, 0x6c, 0x18, 0xd4, 0xd2, 0x33, 0x8c, 0xfb, 0x49, 0x6e, 0x07, 0x03, 0x52, 0x68, 0x71, 0xc9, 0x78, 0x4b, 0xac, 0x8e, 0xba, 0xe8, 0x27, 0x9c, 0xf2, 0x71, 0x3a, 0xf3, 0xcc, 0x2d, 0x44, 0x0e, + 0x8c, 0xd2, 0x00, 0x86, 0x7b, 0x85, 0x18, 0xaa, 0xd3, 0xb9, 0xe2, 0x85, 0x02, 0x7d, 0xa0, 0xad, 0xd9, 0xf0, 0x22, 0x9e, 0xd4, 0xe8, 0x42, 0xd0, 0x5e, 0x22, 0x6a, 0xda, 0xc1, 0x3a, 0x39, 0x52, + 0xe3, 0x83, 0x5c, 0x8f, 0xb0, 0xa4, 0x28, 0x74, 0xc9, 0x4c, 0x66, 0x1b, 0x39, 0xdf, 0x7b, 0x72, 0x88, 0x7d, 0x22, 0x7d, 0x58, 0x3c, 0xe6, 0xb3, 0xbd, 0x65, 0xf7, 0x95, 0x10, 0x7b, 0xd0, 0x93, + 0x38, 0x9b, 0xfe, 0xfd, 0x17, 0x68, 0xa5, 0x71, 0x6f, 0x68, 0x5b, 0x17, 0x4e, 0xd2, 0x3e, 0x94, 0xa5, 0x95, 0x6e, 0x29, 0xbb, 0x2d, 0xdb, 0x79, 0x21, 0x03, 0xe6, 0x2f, 0x68, 0x92, 0x8a, 0xcc, + 0x60, 0x3e, 0xec, 0x2f, 0xf5, 0x6d, 0xb1, 0x4c, 0x08, 0xb7, 0xcb, 0xe4, 0xe2, 0xb4, 0xf2, 0xe0, 0xea, 0xee, 0x54, 0x16, 0x2e, 0x95, 0xbb, 0x35, 0xef, 0x36, 0x30, 0x3e, 0xe3, 0xe6, 0xcc, 0x61, + 0x06, 0x13, 0x73, 0x87, 0x6f, 0x7a, 0x09, 0x6a, 0x8a, 0xf5, 0x7d, 0x78, 0x2f, 0x8c, 0x82, 0x03, 0xde, 0x93, 0x42, 0x3a, 0x37, 0x91, 0x22, 0xfe, 0x7d, 0xad, 0x77, 0x0c, 0x36, 0x90, 0xf9, 0x78, + 0x22, 0x84, 0x60, 0xd0, 0x25, 0xce, 0x93, 0xb1, 0xb3, 0x36, 0xc5, 0x73, 0xe4, 0xe5, 0x58, 0x40, 0xea, 0x65, 0xcf, 0xdd, 0x61, 0x22, 0xc6, 0x72, 0xc9, 0x12, 0xf5, 0x29, 0x39, 0xd9, 0xea, 0x5b, + 0xe0, 0x62, 0x10, 0xf5, 0xe7, 0xed, 0xb6, 0x5b, 0x66, 0x94, 0x5d, 0x70, 0x56, 0xf5, 0x59, 0xa7, 0xd6, 0x92, 0x53, 0xf4, 0xbd, 0xbc, 0x57, 0x9d, 0xe9, 0x64, 0xf3, 0xe9, 0x3a, 0x86, 0xfa, 0x38, + 0xb6, 0xa2, 0xc0, 0xb5, 0x43, 0x38, 0xdc, 0xe0, 0x93, 0xf0, 0xb4, 0x68, 0x4e, 0xe3, 0x61, 0x44, 0x9f, 0x16, 0xc2, 0x79, 0xa7, 0x2b, 0x77, 0x31, 0xe4, 0x46, 0x00, 0xa7, 0x02, 0x77, 0x68, 0xfd, + 0xd0, 0xf6, 0x43, 0xed, 0x10, 0x06, 0x4b, 0x98, 0xa9, 0xda, 0x03, 0x2f, 0x1f, 0x5d, 0xea, 0xd3, 0x11, 0xe1, 0x77, 0x33, 0x50, 0x94, 0xdb, 0x4e, 0x38, 0x51, 0x4e, 0xae, 0x15, 0xa8, 0xf8, 0xec, + 0xf2, 0xf2, 0x41, 0x4e, 0x37, 0x8e, 0xfb, 0xf9, 0x97, 0xb1, 0x06, 0x6b, 0x6f, 0x69, 0xd6, 0x69, 0x09, 0xa4, 0x7e, 0x29, 0x8a, 0x7f, 0xec, 0x96, 0x1a, 0x83, 0x78, 0x2e, 0x0e, 0x47, 0x0f, 0xe0, + 0x71, 0xde, 0xcf, 0x4b, 0x26, 0xac, 0xa6, 0xed, 0x68, 0x83, 0x59, 0xe1, 0x08, 0x50, 0x55, 0xfd, 0x2b, 0x5a, 0xe9, 0xf4, 0x91, 0x87, 0x49, 0x89, 0x7a, 0xf1, 0x33, 0x60, 0x60, 0x53, 0xd5, 0xf6, + 0xa8, 0x52, 0x8c, 0xcb, 0x31, 0xab, 0x7f, 0x3f, 0x2d, 0x89, 0xa9, 0x5c, 0x5f, 0x05, 0xb1, 0x57, 0x00, 0xe5, 0x32, 0xad, 0x81, 0xd5, 0x9d, 0x9d, 0xb8, 0xa2, 0xc2, 0x9c, 0xac, 0x93, 0x6e, 0x3f, + 0x33, 0xdf, 0xe2, 0x4b, 0x0b, 0x1b, 0x71, 0x90, 0x2d, 0xc9, 0xc3, 0x0e, 0xc8, 0xc7, 0x0b, 0xda, 0xba, 0x48, 0x4f, 0xcd, 0x2b, 0x94, 0x6d, 0x73, 0x5f, 0x16, 0xee, 0xad, 0x04, 0x03, 0x1c, 0xaf, + 0xde, 0x9e, 0xe0, 0x16, 0x96, 0xec, 0x9f, 0x0a, 0x8d, 0x5f, 0x36, 0xb6, 0x9c, 0x64, 0x2f, 0xfd, 0x0a, 0xd0, 0xd2, 0x54, 0x4f, 0x5e, 0x7f, 0xd8, 0x9a, 0x80, 0x49, 0x8e, 0xf6, 0x8e, 0x18, 0x16, + 0x17, 0xfa, 0xd4, 0x1e, 0x0b, 0xd5, 0x9b, 0xaa, 0xff, 0xee, 0xfe, 0x2f, 0x99, 0x72, 0x4c, 0x71, 0x9d, 0x47, 0xa2, 0xec, 0xba, 0x72, 0x1d, 0x76, 0xf2, 0x37, 0xeb, 0xa7, 0x3d, 0xb4, 0x7d, 0x88, + 0xb6, 0x99, 0xe3, 0x58, 0x2b, 0x07, 0x3c, 0x7e, 0xad, 0x2a, 0x5b, 0x3c, 0xf0, 0x24, 0x46, 0x63, 0x96, 0xf9, 0xf2, 0x82, 0x6c, 0xb7, 0x54, 0xf6, 0x60, 0x18, 0xe9, 0x50, 0x3f, 0x4a, 0xd1, 0xf9, + 0xd9, 0x21, 0x21, 0xaa, 0x99, 0x56, 0x50, 0x60, 0x51, 0xd5, 0x96, 0xff, 0xd4, 0x67, 0xe1, 0xaa, 0x8d, 0x96, 0x4c, 0x17, 0x67, 0xc9, 0x25, 0xb4, 0x68, 0xbb, 0xc9, 0x85, 0x06, 0x00, 0xc8, 0x43, + 0x49, 0x05, 0x41, 0xe8, 0x55, 0x5a, 0x3d, 0x8b, 0xd9, 0xf1, 0x87, 0x91, 0xef, 0x9e, 0xbd, 0x35, 0x94, 0xe7, 0x4c, 0x1f, 0xe3, 0xd3, 0xb8, 0x09, 0x40, 0xa8, 0xa0, 0x79, 0xf8, 0xd2, 0xca, 0x8d, + 0x30, 0x13, 0x4f, 0xc6, 0x6f, 0x87, 0x00, 0x81, 0x26, 0xe4, 0x3b, 0xd0, 0x6e, 0xb6, 0xe4, 0x1c, 0x3a, 0x70, 0xfa, 0x47, 0x39, 0x31, 0x9b, 0xf1, 0xa9, 0x32, 0xf0, 0x2c, 0x30, 0x64, 0x56, 0x56, + 0x0c, 0xda, 0x44, 0xdd, 0xac, 0x43, 0xed, 0x6d, 0x90, 0x04, 0x45, 0xf5, 0xbf, 0x85, 0xbb, 0x0c, 0xe3, 0x25, 0x94, 0x74, 0x36, 0xe0, 0xd0, 0x68, 0x5e, 0x41, 0xb1, 0x6b, 0xc7, 0x16, 0x95, 0x18, + 0x25, 0x9e, 0x57, 0x34, 0xfd, 0xce, 0x08, 0x0f, 0xfe, 0x85, 0x19, 0x1b, 0x1d, 0x8d, 0x8d, 0xe4, 0xdb, 0x48, 0x14, 0x3f, 0xb5, 0x64, 0x03, 0x8a, 0xce, 0x80, 0x10, 0x4d, 0x3a, 0x8d, 0x07, 0x12, + 0x45, 0xe2, 0xaa, 0x56, 0xc7, 0x19, 0x33, 0xf4, 0xdc, 0xf9, 0x25, 0xee, 0xe8, 0x44, 0xc8, 0x0f, 0xdd, 0xf3, 0x25, 0x1f, 0x74, 0x00, 0x6a, 0x23, 0x41, 0x33, 0x18, 0xbb, 0xfd, 0x2e, 0xd9, 0xe0, + 0x53, 0x51, 0xb5, 0xaa, 0xeb, 0xcc, 0x77, 0xcf, 0xac, 0x8d, 0x5f, 0x03, 0x64, 0x23, 0x1a, 0x50, 0xea, 0x86, 0x47, 0xc7, 0x2f, 0x71, 0x3e, 0x81, 0x7a, 0x20, 0x75, 0x32, 0x30, 0x29, 0xe3, 0xb8, + 0x8b, 0x72, 0x44, 0x22, 0x64, 0xc5, 0x97, 0xb0, 0xf1, 0xfc, 0x09, 0xf9, 0x40, 0x1c, 0xe8, 0x8a, 0xc9, 0x7c, 0x55, 0x22, 0xa5, 0x63, 0x64, 0x52, 0x3c, 0x37, 0xfe, 0xa2, 0xd6, 0xbd, 0x06, 0xb2, + }, + }, + { + .name = "Kyber Round 2, 1024 KAT 1 (PKCS#8/SPKI)", + .version = 0, + .keyform = 0, + .pk_len = 0, + .sk_len = 0, + .pkcs8_len = 4849, + .pkcs8 = { + 0x30, 0x82, 0x12, 0xed, 0x02, 0x01, 0x00, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x05, 0x04, 0x04, 0x05, 0x00, 0x04, 0x82, 0x12, 0xd5, 0x30, 0x82, 0x12, 0xd1, + 0x02, 0x01, 0x00, 0x03, 0x82, 0x0c, 0x61, 0x00, 0x07, 0x63, 0x8f, 0xb6, 0x98, 0x68, 0xf3, 0xd3, 0x20, 0xe5, 0x86, 0x2b, 0xd9, 0x69, 0x33, 0xfe, 0xb3, 0x11, 0xb3, 0x62, 0x09, 0x3c, 0x9b, 0x5d, + 0x50, 0x17, 0x0b, 0xce, 0xd4, 0x3f, 0x1b, 0x53, 0x6d, 0x9a, 0x20, 0x4b, 0xb1, 0xf2, 0x26, 0x95, 0x95, 0x0b, 0xa1, 0xf2, 0xa9, 0xe8, 0xeb, 0x82, 0x8b, 0x28, 0x44, 0x88, 0x76, 0x0b, 0x3f, 0xc8, + 0x4f, 0xab, 0xa0, 0x42, 0x75, 0xd5, 0x62, 0x8e, 0x39, 0xc5, 0xb2, 0x47, 0x13, 0x74, 0x28, 0x3c, 0x50, 0x32, 0x99, 0xc0, 0xab, 0x49, 0xb6, 0x6b, 0x8b, 0xbb, 0x56, 0xa4, 0x18, 0x66, 0x24, 0xf9, + 0x19, 0xa2, 0xba, 0x59, 0xbb, 0x08, 0xd8, 0x55, 0x18, 0x80, 0xc2, 0xbe, 0xfc, 0x4f, 0x87, 0xf2, 0x5f, 0x59, 0xab, 0x58, 0x7a, 0x79, 0xc3, 0x27, 0xd7, 0x92, 0xd5, 0x4c, 0x97, 0x4a, 0x69, 0x26, + 0x2f, 0xf8, 0xa7, 0x89, 0x38, 0x28, 0x9e, 0x9a, 0x87, 0xb6, 0x88, 0xb0, 0x83, 0xe0, 0x59, 0x5f, 0xe2, 0x18, 0xb6, 0xbb, 0x15, 0x05, 0x94, 0x1c, 0xe2, 0xe8, 0x1a, 0x5a, 0x64, 0xc5, 0xaa, 0xc6, + 0x04, 0x17, 0x25, 0x69, 0x85, 0x34, 0x9e, 0xe4, 0x7a, 0x52, 0x42, 0x0a, 0x5f, 0x97, 0x47, 0x7b, 0x72, 0x36, 0xac, 0x76, 0xbc, 0x70, 0xe8, 0x28, 0x87, 0x29, 0x28, 0x7e, 0xe3, 0xe3, 0x4a, 0x3d, + 0xbc, 0x36, 0x83, 0xc0, 0xb7, 0xb1, 0x00, 0x29, 0xfc, 0x20, 0x34, 0x18, 0x53, 0x7e, 0x74, 0x66, 0xba, 0x63, 0x85, 0xa8, 0xff, 0x30, 0x1e, 0xe1, 0x27, 0x08, 0xf8, 0x2a, 0xaa, 0x1e, 0x38, 0x0f, + 0xc7, 0xa8, 0x8f, 0x8f, 0x20, 0x5a, 0xb7, 0xe8, 0x8d, 0x7e, 0x95, 0x95, 0x2a, 0x55, 0xba, 0x20, 0xd0, 0x9b, 0x79, 0xa4, 0x71, 0x41, 0xd6, 0x2b, 0xf6, 0xeb, 0x7d, 0xd3, 0x07, 0xb0, 0x8e, 0xca, + 0x13, 0xa5, 0xbc, 0x5f, 0x6b, 0x68, 0x58, 0x1c, 0x68, 0x65, 0xb2, 0x7b, 0xbc, 0xdd, 0xab, 0x14, 0x2f, 0x4b, 0x2c, 0xbf, 0xf4, 0x88, 0xc8, 0xa2, 0x27, 0x05, 0xfa, 0xa9, 0x8a, 0x2b, 0x9e, 0xea, + 0x35, 0x30, 0xc7, 0x66, 0x62, 0x33, 0x5c, 0xc7, 0xea, 0x3a, 0x00, 0x77, 0x77, 0x25, 0xeb, 0xcc, 0xcd, 0x2a, 0x46, 0x36, 0xb2, 0xd9, 0x12, 0x2f, 0xf3, 0xab, 0x77, 0x12, 0x3c, 0xe0, 0x88, 0x3c, + 0x19, 0x11, 0x11, 0x5e, 0x50, 0xc9, 0xe8, 0xa9, 0x41, 0x94, 0xe4, 0x8d, 0xd0, 0xd0, 0x9c, 0xff, 0xb3, 0xad, 0xcd, 0x2c, 0x1e, 0x92, 0x43, 0x09, 0x03, 0xd0, 0x7a, 0xdb, 0xf0, 0x05, 0x32, 0x03, + 0x15, 0x75, 0xaa, 0x7f, 0x9e, 0x7b, 0x5a, 0x1f, 0x33, 0x62, 0xde, 0xc9, 0x36, 0xd4, 0x04, 0x3c, 0x05, 0xf2, 0x47, 0x6c, 0x07, 0x57, 0x8b, 0xc9, 0xcb, 0xaf, 0x2a, 0xb4, 0xe3, 0x82, 0x72, 0x7a, + 0xd4, 0x16, 0x86, 0xa9, 0x6b, 0x25, 0x48, 0x82, 0x0b, 0xb0, 0x3b, 0x32, 0xf1, 0x1b, 0x28, 0x11, 0xad, 0x62, 0xf4, 0x89, 0xe9, 0x51, 0x63, 0x2a, 0xba, 0x0d, 0x1d, 0xf8, 0x96, 0x80, 0xcc, 0x8a, + 0x8b, 0x53, 0xb4, 0x81, 0xd9, 0x2a, 0x68, 0xd7, 0x0b, 0x4e, 0xa1, 0xc3, 0xa6, 0xa5, 0x61, 0xc0, 0x69, 0x28, 0x82, 0xb5, 0xca, 0x8c, 0xc9, 0x42, 0xa8, 0xd4, 0x95, 0xaf, 0xcb, 0x06, 0xde, 0x89, + 0x49, 0x8f, 0xb9, 0x35, 0xb7, 0x75, 0x90, 0x8f, 0xe7, 0xa0, 0x3e, 0x32, 0x4d, 0x54, 0xcc, 0x19, 0xd4, 0xe1, 0xaa, 0xbd, 0x35, 0x93, 0xb3, 0x8b, 0x19, 0xee, 0x13, 0x88, 0xfe, 0x49, 0x2b, 0x43, + 0x12, 0x7e, 0x5a, 0x50, 0x42, 0x53, 0x78, 0x6a, 0x0d, 0x69, 0xad, 0x32, 0x60, 0x1c, 0x28, 0xe2, 0xc8, 0x85, 0x04, 0xa5, 0xba, 0x59, 0x97, 0x06, 0x02, 0x3a, 0x61, 0x36, 0x3e, 0x17, 0xc6, 0xb9, + 0xbb, 0x59, 0xbd, 0xc6, 0x97, 0x45, 0x2c, 0xd0, 0x59, 0x45, 0x19, 0x83, 0xd7, 0x38, 0xca, 0x3f, 0xd0, 0x34, 0xe3, 0xf5, 0x98, 0x88, 0x54, 0xca, 0x05, 0x03, 0x1d, 0xb0, 0x96, 0x11, 0x49, 0x89, + 0x88, 0x19, 0x7c, 0x6b, 0x30, 0xd2, 0x58, 0xdf, 0xe2, 0x62, 0x65, 0x54, 0x1c, 0x89, 0xa4, 0xb3, 0x1d, 0x68, 0x64, 0xe9, 0x38, 0x9b, 0x03, 0xcb, 0x74, 0xf7, 0xec, 0x43, 0x23, 0xfb, 0x94, 0x21, + 0xa4, 0xb9, 0x79, 0x0a, 0x26, 0xd1, 0x7b, 0x03, 0x98, 0xa2, 0x67, 0x67, 0x35, 0x09, 0x09, 0xf8, 0x4d, 0x57, 0xb6, 0x69, 0x4d, 0xf8, 0x30, 0x66, 0x4c, 0xa8, 0xb3, 0xc3, 0xc0, 0x3e, 0xd2, 0xae, + 0x67, 0xb8, 0x90, 0x06, 0x86, 0x8a, 0x68, 0x52, 0x7c, 0xcd, 0x66, 0x64, 0x59, 0xab, 0x7f, 0x05, 0x66, 0x71, 0x00, 0x0c, 0x61, 0x64, 0xd3, 0xa7, 0xf2, 0x66, 0xa1, 0x4d, 0x97, 0xcb, 0xd7, 0x00, + 0x4d, 0x6c, 0x92, 0xca, 0xca, 0x77, 0x0b, 0x84, 0x4a, 0x4f, 0xa9, 0xb1, 0x82, 0xe7, 0xb1, 0x8c, 0xa8, 0x85, 0x08, 0x2a, 0xc5, 0x64, 0x6f, 0xcb, 0x4a, 0x14, 0xe1, 0x68, 0x5f, 0xeb, 0x0c, 0x9c, + 0xe3, 0x37, 0x2a, 0xb9, 0x53, 0x65, 0xc0, 0x4f, 0xd8, 0x30, 0x84, 0xf8, 0x0a, 0x23, 0xff, 0x10, 0xa0, 0x5b, 0xf1, 0x5f, 0x7f, 0xa5, 0xac, 0xc6, 0xc0, 0xcb, 0x46, 0x2c, 0x33, 0xca, 0x52, 0x4f, + 0xa6, 0xb8, 0xbb, 0x35, 0x90, 0x43, 0xba, 0x68, 0x60, 0x9e, 0xaa, 0x25, 0x36, 0xe8, 0x1d, 0x08, 0x46, 0x3b, 0x19, 0x65, 0x3b, 0x54, 0x35, 0xba, 0x94, 0x6c, 0x9a, 0xdd, 0xeb, 0x20, 0x2b, 0x04, + 0xb0, 0x31, 0xcc, 0x96, 0x0d, 0xcc, 0x12, 0xe4, 0x51, 0x8d, 0x42, 0x8b, 0x32, 0xb2, 0x57, 0xa4, 0xfc, 0x73, 0x13, 0xd3, 0xa7, 0x98, 0x0d, 0x80, 0x08, 0x2e, 0x93, 0x4f, 0x9d, 0x95, 0xc3, 0x2b, + 0x0a, 0x01, 0x91, 0xa2, 0x36, 0x04, 0x38, 0x4d, 0xd9, 0xe0, 0x79, 0xbb, 0xba, 0xa2, 0x66, 0xd1, 0x4c, 0x3f, 0x75, 0x6b, 0x9f, 0x21, 0x33, 0x10, 0x74, 0x33, 0xa4, 0xe8, 0x3f, 0xa7, 0x18, 0x72, + 0x82, 0xa8, 0x09, 0x20, 0x3a, 0x4f, 0xaf, 0x84, 0x18, 0x51, 0x83, 0x3d, 0x12, 0x1a, 0xc3, 0x83, 0x84, 0x3a, 0x5e, 0x55, 0xbc, 0x23, 0x81, 0x42, 0x5e, 0x16, 0xc7, 0xdb, 0x4c, 0xc9, 0xab, 0x5c, + 0x1b, 0x0d, 0x91, 0xa4, 0x7e, 0x2b, 0x8d, 0xe0, 0xe5, 0x82, 0xc8, 0x6b, 0x6b, 0x0d, 0x90, 0x7b, 0xb3, 0x60, 0xb9, 0x7f, 0x40, 0xab, 0x5d, 0x03, 0x8f, 0x6b, 0x75, 0xc8, 0x14, 0xb2, 0x7d, 0x9b, + 0x96, 0x8d, 0x41, 0x98, 0x32, 0xbc, 0x8c, 0x2b, 0xee, 0x60, 0x5e, 0xf6, 0xe5, 0x05, 0x9d, 0x33, 0x10, 0x0d, 0x90, 0x48, 0x5d, 0x37, 0x84, 0x50, 0x01, 0x42, 0x21, 0x73, 0x6c, 0x07, 0x40, 0x7c, + 0xac, 0x26, 0x04, 0x08, 0xaa, 0x64, 0x92, 0x66, 0x19, 0x78, 0x8b, 0x86, 0x01, 0xc2, 0xa7, 0x52, 0xd1, 0xa6, 0xcb, 0xf8, 0x20, 0xd7, 0xc7, 0xa0, 0x47, 0x16, 0x20, 0x32, 0x25, 0xb3, 0x89, 0x5b, + 0x93, 0x42, 0xd1, 0x47, 0xa8, 0x18, 0x5c, 0xfc, 0x1b, 0xb6, 0x5b, 0xa0, 0x6b, 0x41, 0x42, 0x33, 0x99, 0x03, 0xc0, 0xac, 0x46, 0x51, 0x38, 0x5b, 0x45, 0xd9, 0x8a, 0x8b, 0x19, 0xd2, 0x8c, 0xd6, + 0xba, 0xb0, 0x88, 0x78, 0x7f, 0x7e, 0xe1, 0xb1, 0x24, 0x61, 0x76, 0x6b, 0x43, 0xcb, 0xcc, 0xb9, 0x64, 0x34, 0x42, 0x7d, 0x93, 0xc0, 0x65, 0x55, 0x06, 0x88, 0xf6, 0x94, 0x8e, 0xd1, 0xb5, 0x47, + 0x5a, 0x42, 0x5f, 0x1b, 0x85, 0x20, 0x9d, 0x06, 0x1c, 0x08, 0xb5, 0x6c, 0x1c, 0xc0, 0x69, 0xf6, 0xc0, 0xa7, 0xc6, 0xf2, 0x93, 0x58, 0xca, 0xb9, 0x11, 0x08, 0x77, 0x32, 0xa6, 0x49, 0xd2, 0x7c, + 0x9b, 0x98, 0xf9, 0xa4, 0x88, 0x79, 0x38, 0x7d, 0x9b, 0x00, 0xc2, 0x59, 0x59, 0xa7, 0x16, 0x54, 0xd6, 0xf6, 0xa9, 0x46, 0x16, 0x45, 0x13, 0xe4, 0x7a, 0x75, 0xd0, 0x05, 0x98, 0x6c, 0x23, 0x63, + 0xc0, 0x9f, 0x6b, 0x53, 0x7e, 0xca, 0x78, 0xb9, 0x30, 0x3a, 0x5f, 0xa4, 0x57, 0x60, 0x8a, 0x58, 0x6a, 0x65, 0x3a, 0x34, 0x7d, 0xb0, 0x4d, 0xfc, 0xc1, 0x91, 0x75, 0xb3, 0xa3, 0x01, 0x17, 0x25, + 0x36, 0x06, 0x2a, 0x65, 0x8a, 0x95, 0x27, 0x75, 0x70, 0xc8, 0x85, 0x2c, 0xa8, 0x97, 0x3f, 0x4a, 0xe1, 0x23, 0xa3, 0x34, 0x04, 0x7d, 0xd7, 0x11, 0xc8, 0x92, 0x7a, 0x63, 0x4a, 0x03, 0x38, 0x8a, + 0x52, 0x7b, 0x03, 0x4b, 0xf7, 0xa8, 0x17, 0x0f, 0xa7, 0x02, 0xc1, 0xf7, 0xc2, 0x3e, 0xc3, 0x2d, 0x18, 0xa2, 0x37, 0x48, 0x90, 0xbe, 0x9c, 0x78, 0x7a, 0x94, 0x09, 0xc8, 0x2d, 0x19, 0x2c, 0x4b, + 0xb7, 0x05, 0xa2, 0xf9, 0x96, 0xce, 0x40, 0x5d, 0x85, 0xa4, 0xc1, 0xa1, 0xab, 0x9b, 0x6a, 0xeb, 0x49, 0xcc, 0xe1, 0xc2, 0xf8, 0xa9, 0x7c, 0x35, 0x16, 0xc7, 0x2a, 0x00, 0xa4, 0x62, 0x63, 0xba, + 0xa6, 0x96, 0xbf, 0x25, 0x72, 0x77, 0x19, 0xc3, 0x21, 0x64, 0x23, 0x61, 0x8f, 0xf3, 0x33, 0x80, 0x93, 0x4a, 0x6c, 0x10, 0x54, 0x5c, 0x4c, 0x5c, 0x51, 0x55, 0xb1, 0x24, 0x86, 0x18, 0x1f, 0xc7, + 0xa2, 0x31, 0x98, 0x73, 0x97, 0x8b, 0x6a, 0x2a, 0x67, 0x49, 0x0f, 0x82, 0x56, 0xbd, 0x21, 0x96, 0xfe, 0x17, 0x92, 0xa4, 0xc0, 0x00, 0x77, 0xb8, 0x12, 0xea, 0xe8, 0xbe, 0xd3, 0x57, 0x24, 0x99, + 0x68, 0x4a, 0xb3, 0x37, 0x18, 0x76, 0x76, 0x1e, 0x45, 0x0c, 0x9f, 0x9d, 0x27, 0x68, 0xa3, 0x68, 0x06, 0xd7, 0xab, 0x20, 0x46, 0xc9, 0x1f, 0x17, 0x59, 0x9e, 0x9a, 0xc5, 0x92, 0x99, 0x08, 0x08, + 0xdc, 0xd7, 0xb4, 0xd0, 0x91, 0x90, 0x72, 0xf1, 0x4e, 0xc3, 0x61, 0x77, 0x3b, 0x72, 0x52, 0x44, 0x4c, 0x32, 0x3c, 0x30, 0x83, 0x26, 0xf4, 0xa3, 0x0f, 0x86, 0x80, 0xd2, 0xf7, 0x48, 0xf5, 0x6a, + 0x13, 0x2b, 0x82, 0x67, 0x4e, 0xd0, 0x18, 0x46, 0x20, 0xb8, 0x2a, 0xd2, 0xcb, 0x18, 0x2c, 0x97, 0xb4, 0x81, 0x62, 0x66, 0x47, 0x49, 0x12, 0x90, 0xa0, 0x11, 0xcc, 0x73, 0x82, 0x86, 0x85, 0xa8, + 0xc3, 0x67, 0xa5, 0xb9, 0xcf, 0x8d, 0x62, 0x1b, 0x0d, 0x5c, 0x1e, 0xff, 0x03, 0x17, 0x27, 0x58, 0xbd, 0x00, 0x49, 0x78, 0xc2, 0x51, 0xcd, 0x51, 0x34, 0x22, 0x28, 0x98, 0x9c, 0xae, 0x63, 0x32, + 0xac, 0x48, 0x64, 0x37, 0xcb, 0x5c, 0x57, 0xd4, 0x30, 0x74, 0x62, 0x86, 0x52, 0x53, 0xbe, 0x21, 0x7b, 0x35, 0x15, 0xc7, 0x3d, 0xf4, 0x05, 0xb7, 0xf2, 0x82, 0x17, 0xad, 0x0b, 0x8c, 0xf6, 0x0c, + 0x2f, 0xff, 0xaa, 0x0a, 0x00, 0x48, 0xb1, 0xfb, 0x4a, 0xcd, 0xcd, 0xc3, 0x8b, 0x52, 0x50, 0xcf, 0xec, 0x35, 0x6a, 0x6d, 0xe2, 0x6c, 0xfa, 0x7a, 0x58, 0x8f, 0xdc, 0x86, 0xf9, 0x8c, 0x85, 0x4a, + 0xc6, 0x4c, 0x7b, 0xfa, 0xa9, 0x6f, 0x5a, 0x32, 0xcc, 0x06, 0x10, 0x93, 0x4b, 0xaa, 0x6a, 0x58, 0x6b, 0x9a, 0x20, 0x54, 0xf1, 0x3b, 0xa2, 0x74, 0x17, 0x4a, 0xa0, 0xd2, 0xb3, 0xa8, 0x1b, 0x96, + 0xa9, 0x40, 0x66, 0x6f, 0x78, 0x9b, 0x5a, 0x6b, 0xcd, 0xc0, 0xa6, 0xa0, 0x17, 0x8a, 0x0c, 0x9a, 0x02, 0x57, 0x8a, 0x49, 0x3f, 0x6e, 0xea, 0x0d, 0x2e, 0x6c, 0x13, 0x95, 0x1c, 0x9f, 0x24, 0x9a, + 0x5e, 0x8d, 0xd7, 0x1d, 0xd4, 0x9a, 0x74, 0x2d, 0x45, 0x1f, 0x1a, 0xbb, 0xa1, 0x9a, 0xf8, 0xc5, 0x47, 0x85, 0x5e, 0x0a, 0xfc, 0x72, 0x8e, 0x90, 0xab, 0xb4, 0x99, 0xc9, 0xbe, 0xeb, 0x76, 0x6f, + 0x47, 0x29, 0xcd, 0xa2, 0x22, 0x63, 0xe3, 0x24, 0xda, 0x18, 0x71, 0x2d, 0x31, 0x6e, 0x98, 0xdc, 0x7a, 0xc8, 0xc3, 0xca, 0x47, 0x37, 0x0e, 0xbd, 0x77, 0x0c, 0xe3, 0x2b, 0x3b, 0xd4, 0xb1, 0xa0, + 0xc9, 0x52, 0x9a, 0xc6, 0xec, 0x8e, 0xe0, 0x28, 0xb1, 0xcd, 0xb2, 0x65, 0x1c, 0xb5, 0xa6, 0xbb, 0x3c, 0x0c, 0x6d, 0xf1, 0x24, 0x0a, 0x3b, 0x91, 0x4b, 0x56, 0x56, 0xc0, 0xdc, 0x51, 0xc2, 0xb9, + 0x1b, 0xfc, 0xbc, 0x37, 0xa4, 0x66, 0x02, 0x87, 0xd4, 0x4f, 0x81, 0xf8, 0x53, 0xc7, 0xf4, 0x9a, 0x6d, 0x06, 0x03, 0xd6, 0xd7, 0x23, 0xcb, 0xec, 0x01, 0x5f, 0xbc, 0x43, 0x4a, 0x38, 0x24, 0x1c, + 0x10, 0x9c, 0x7e, 0xd5, 0xb1, 0xcc, 0x46, 0x1a, 0x2c, 0xcb, 0x9a, 0xb7, 0x14, 0x0f, 0x19, 0xf3, 0x7a, 0x13, 0xbb, 0x70, 0x1e, 0x14, 0x2b, 0xd5, 0x4b, 0x64, 0xec, 0x6b, 0x76, 0xfe, 0xc3, 0x3b, + 0x69, 0xc2, 0x91, 0x8c, 0xb0, 0x17, 0xc4, 0x14, 0x34, 0x23, 0x00, 0x9a, 0x3c, 0x07, 0xb5, 0xc1, 0x81, 0xb0, 0xc1, 0xeb, 0x49, 0x4a, 0x62, 0xab, 0xc8, 0x39, 0x13, 0x97, 0x08, 0x9e, 0xa6, 0x64, + 0x09, 0x67, 0xc1, 0x20, 0x49, 0x84, 0xcd, 0x48, 0x4c, 0xcc, 0xb0, 0x0a, 0x9a, 0x17, 0xd0, 0x87, 0x21, 0x84, 0x28, 0xef, 0x3b, 0xb7, 0x08, 0x78, 0x3e, 0x12, 0x82, 0x71, 0x04, 0x41, 0x73, 0x75, + 0xb6, 0x95, 0x6f, 0xb5, 0x00, 0x53, 0xd0, 0x48, 0xa4, 0x79, 0x14, 0x95, 0x82, 0x4a, 0x34, 0x80, 0xa5, 0xb7, 0x83, 0x02, 0x56, 0x09, 0x6f, 0xdd, 0x72, 0x5c, 0x30, 0x8b, 0x3b, 0xe8, 0x4a, 0x07, + 0xf3, 0x63, 0x2e, 0x24, 0x95, 0xc6, 0x2e, 0x96, 0x39, 0x9d, 0x80, 0xbf, 0xa7, 0x45, 0xb9, 0x84, 0x1a, 0x18, 0x33, 0xbc, 0x1d, 0x27, 0xba, 0x45, 0xa5, 0x21, 0x68, 0xee, 0x59, 0x00, 0x6c, 0x3a, + 0x3a, 0x8c, 0x4a, 0x5a, 0x4f, 0x50, 0x88, 0xfc, 0x73, 0x71, 0x81, 0xab, 0x51, 0x96, 0xf7, 0xb1, 0xb4, 0x9a, 0x2e, 0xd8, 0x13, 0x13, 0x4e, 0x11, 0x2f, 0x73, 0x0b, 0x99, 0x1c, 0x54, 0xa7, 0x19, + 0x6b, 0xcf, 0x5f, 0xc7, 0x6e, 0x13, 0x4c, 0x58, 0x43, 0xe1, 0x69, 0x88, 0x51, 0xb2, 0xf8, 0x69, 0xaf, 0xaf, 0xb0, 0x27, 0x87, 0xd9, 0xc2, 0xf1, 0x36, 0x90, 0x2d, 0xc7, 0xa7, 0xf3, 0xd6, 0x21, + 0x56, 0xd1, 0x5e, 0xc3, 0x09, 0x56, 0x40, 0x92, 0xc6, 0x1d, 0x83, 0xb0, 0x98, 0x6c, 0x48, 0x40, 0x99, 0x81, 0xf3, 0xc1, 0x86, 0x88, 0x0a, 0x2f, 0x63, 0xd5, 0x86, 0x0a, 0xb6, 0x01, 0xde, 0xac, + 0x2b, 0x6b, 0xa1, 0xb4, 0x28, 0x17, 0x9d, 0x73, 0x53, 0x3e, 0xb7, 0xa3, 0xa5, 0x11, 0x3b, 0x85, 0x61, 0xf1, 0x0b, 0x45, 0xc3, 0xcd, 0xe2, 0x82, 0xb6, 0xea, 0xd6, 0xab, 0x6c, 0x60, 0x4f, 0x09, + 0xc1, 0x7b, 0xfd, 0xa0, 0x83, 0x13, 0xa3, 0x26, 0x07, 0x67, 0x5a, 0xdf, 0x64, 0x31, 0xca, 0x87, 0x18, 0xe9, 0xc4, 0x3a, 0x73, 0x73, 0x32, 0x27, 0xe7, 0x3b, 0xc6, 0x1a, 0xc8, 0x45, 0xba, 0x90, + 0x77, 0x55, 0xce, 0xc6, 0x89, 0x25, 0xe5, 0xe2, 0xbf, 0xe9, 0x12, 0x95, 0x9d, 0xb8, 0x6f, 0xbf, 0xe2, 0x15, 0x6f, 0xd5, 0xbb, 0xdb, 0xf0, 0xc9, 0xdf, 0x8b, 0x53, 0x02, 0xaa, 0x8d, 0x90, 0xa2, + 0x2d, 0x12, 0x27, 0x0e, 0x00, 0x65, 0x51, 0xe4, 0x76, 0x7e, 0x45, 0x26, 0x8e, 0xd9, 0x69, 0x26, 0x54, 0x44, 0x78, 0x11, 0xea, 0xb8, 0x4f, 0x04, 0x99, 0xa8, 0xa5, 0x8c, 0xf7, 0xc0, 0x4a, 0x59, + 0x56, 0x98, 0x52, 0x80, 0x45, 0xf2, 0x98, 0x97, 0xc8, 0xfa, 0x96, 0xd0, 0x6c, 0xce, 0x51, 0xe6, 0xaf, 0xea, 0xc4, 0x33, 0x95, 0x89, 0xc9, 0x41, 0xc8, 0x55, 0x63, 0xd7, 0x0f, 0xac, 0xe1, 0x92, + 0x88, 0x94, 0xba, 0xc0, 0x36, 0x19, 0xdf, 0xf4, 0xbe, 0x3f, 0x43, 0x14, 0xa3, 0xf7, 0x35, 0x1a, 0x09, 0xa4, 0x86, 0xb5, 0x04, 0x1e, 0x7c, 0xb2, 0xda, 0x8b, 0x96, 0xbc, 0x66, 0x26, 0xa4, 0x93, + 0x17, 0x35, 0x7c, 0x41, 0x52, 0xa5, 0x1b, 0xa3, 0xc2, 0x8c, 0x7e, 0x0c, 0x9d, 0xb4, 0x1a, 0x06, 0xa2, 0x82, 0x90, 0xf2, 0x18, 0x73, 0x11, 0x07, 0xc9, 0x54, 0xd8, 0xa6, 0x6f, 0x80, 0x1d, 0x7d, + 0xe1, 0x2a, 0x03, 0x71, 0x16, 0x99, 0x0b, 0x6c, 0x53, 0xc1, 0x29, 0xf1, 0x85, 0xc3, 0x45, 0xf2, 0x7e, 0x51, 0x8b, 0x2d, 0x5a, 0x91, 0x25, 0xa0, 0x70, 0x76, 0xd9, 0x91, 0xb7, 0xda, 0xc7, 0xcc, + 0x65, 0xa8, 0x56, 0x2e, 0xfb, 0xcc, 0x32, 0xa9, 0xca, 0x4a, 0xd9, 0x02, 0x63, 0xb0, 0x4a, 0x4f, 0x90, 0x36, 0x11, 0x6c, 0x7b, 0x97, 0x48, 0x04, 0x96, 0x31, 0x75, 0x75, 0x65, 0x0d, 0xcc, 0x21, + 0x52, 0xb5, 0xbc, 0x0e, 0x74, 0x40, 0x7e, 0x12, 0xfa, 0x8e, 0x4f, 0xfc, 0xcc, 0xff, 0x76, 0xc0, 0x1a, 0x97, 0x4b, 0xd6, 0x11, 0x02, 0xe1, 0xf5, 0x29, 0x64, 0x96, 0xc7, 0x1d, 0x07, 0x64, 0xe1, + 0x32, 0x29, 0xff, 0xe7, 0x84, 0x6f, 0x33, 0x6e, 0x34, 0xca, 0xc9, 0x04, 0xca, 0x56, 0x70, 0xf8, 0xcd, 0x50, 0x52, 0x42, 0x7a, 0x79, 0xc0, 0x91, 0xa9, 0x71, 0x21, 0x0c, 0x5c, 0xff, 0x66, 0x7a, + 0xac, 0x24, 0x93, 0x66, 0xe1, 0x0d, 0x2b, 0x11, 0x37, 0x6c, 0xa3, 0x9d, 0x93, 0x52, 0x04, 0xb1, 0x2c, 0xc5, 0x85, 0xe9, 0x40, 0x54, 0x03, 0x62, 0x5f, 0xb3, 0x2c, 0xb5, 0xe5, 0xc3, 0x1b, 0x62, + 0x34, 0x81, 0x60, 0x51, 0x5c, 0xcc, 0x4f, 0xda, 0xf5, 0x70, 0x2d, 0x6b, 0xab, 0x5c, 0x37, 0x3d, 0xb6, 0xf3, 0x50, 0xd3, 0xe6, 0x3a, 0x5c, 0xe3, 0xca, 0x54, 0x74, 0xa0, 0xcf, 0x15, 0x67, 0x04, + 0x2c, 0xa3, 0x25, 0x89, 0x86, 0xff, 0x75, 0xbd, 0xfc, 0xd9, 0x29, 0xe6, 0x46, 0x2f, 0x36, 0xbc, 0xcc, 0x3f, 0x5a, 0x93, 0x35, 0x2a, 0x2b, 0x36, 0xcb, 0x16, 0x2e, 0x18, 0x74, 0xc7, 0x42, 0x87, + 0x0a, 0x97, 0xb1, 0x67, 0xa0, 0x50, 0x37, 0x36, 0x24, 0xea, 0xeb, 0x7e, 0x50, 0x73, 0x25, 0x6b, 0x72, 0x11, 0xb2, 0xd9, 0x4b, 0x84, 0x06, 0xcd, 0x6c, 0x95, 0x33, 0xb1, 0x53, 0x64, 0x08, 0xab, + 0x0a, 0x29, 0xe5, 0xb2, 0xf0, 0xc9, 0x54, 0xec, 0xe0, 0x0f, 0xbb, 0xeb, 0x17, 0x6d, 0x72, 0x4d, 0x4c, 0xf4, 0x43, 0xcf, 0x70, 0x20, 0xd5, 0xfa, 0x70, 0x94, 0xcc, 0x1b, 0x1b, 0xe6, 0x97, 0xba, + 0xd3, 0x36, 0x74, 0xe4, 0x09, 0x9e, 0xc7, 0xbb, 0x18, 0xf4, 0x57, 0x71, 0x28, 0xcd, 0xd9, 0x7c, 0xcd, 0x6d, 0x44, 0x62, 0xe5, 0x60, 0x7c, 0x51, 0x2a, 0x3e, 0x36, 0x24, 0x8e, 0x3d, 0xda, 0xa2, + 0xec, 0x08, 0x9a, 0xef, 0xc4, 0xce, 0x48, 0x5c, 0x49, 0xd7, 0xb0, 0x09, 0xc8, 0xd6, 0x31, 0x15, 0xfc, 0x81, 0xff, 0x3a, 0x62, 0xd1, 0x5a, 0x88, 0x44, 0x1c, 0x03, 0xea, 0x1c, 0x2e, 0x72, 0xc4, + 0x88, 0x39, 0xfc, 0x6a, 0xd7, 0x3a, 0x30, 0x74, 0x4a, 0x62, 0xb7, 0xb2, 0x16, 0x45, 0xa6, 0xaf, 0x7d, 0x61, 0xb6, 0x38, 0x3b, 0x22, 0x1e, 0x21, 0x90, 0x55, 0x57, 0xcd, 0x29, 0xd9, 0x24, 0xa6, + 0x09, 0x86, 0xc5, 0x11, 0xc1, 0xeb, 0xbc, 0x31, 0x6d, 0x56, 0x30, 0xa2, 0x41, 0x43, 0x23, 0xf5, 0x3a, 0xd5, 0x59, 0x94, 0xf6, 0xb3, 0x65, 0x39, 0xf9, 0xc4, 0x40, 0x75, 0xa5, 0x33, 0xe4, 0x81, + 0xc0, 0x84, 0x45, 0xd9, 0xca, 0x9e, 0x9d, 0x38, 0x21, 0x19, 0x38, 0x8b, 0xd1, 0xd7, 0x50, 0x52, 0x21, 0x7a, 0x94, 0x4c, 0xcc, 0x7b, 0xe9, 0x09, 0xe2, 0x19, 0x71, 0x1f, 0xcc, 0x79, 0x24, 0x76, + 0x92, 0x13, 0xa1, 0x92, 0x53, 0x4a, 0x55, 0x80, 0x08, 0x15, 0x7a, 0x39, 0x6e, 0xdf, 0xf4, 0x80, 0xcc, 0x3b, 0x52, 0x0f, 0xf8, 0x18, 0xb3, 0x8b, 0x13, 0x5c, 0x18, 0xa8, 0x0d, 0x51, 0x05, 0xe6, + 0x78, 0x83, 0x6c, 0x39, 0x5c, 0x28, 0xe9, 0x2f, 0x7a, 0x3c, 0x4e, 0x93, 0xc0, 0x10, 0x35, 0xf3, 0x41, 0x11, 0xcc, 0x49, 0x02, 0xd0, 0xc0, 0x33, 0xa6, 0x3f, 0x23, 0x6a, 0x71, 0xda, 0x97, 0x4a, + 0x6f, 0x40, 0x4f, 0x7a, 0xa7, 0xb5, 0xe5, 0x82, 0xc7, 0x58, 0x14, 0x2f, 0xc1, 0x82, 0x6b, 0xba, 0x98, 0xb2, 0x7d, 0x57, 0xc2, 0xe2, 0x10, 0x3e, 0x10, 0xe3, 0x0d, 0x32, 0x79, 0x7b, 0x96, 0x77, + 0x14, 0xd1, 0x56, 0x61, 0x11, 0x13, 0x71, 0xa2, 0xd9, 0xc5, 0x39, 0x98, 0x12, 0x46, 0x46, 0x22, 0x63, 0x5b, 0x44, 0x21, 0x26, 0xb0, 0x98, 0x36, 0xb0, 0x81, 0x82, 0x72, 0x47, 0xd0, 0x54, 0x22, + 0x97, 0x2b, 0xd0, 0x32, 0x0d, 0x8f, 0x42, 0xbf, 0x57, 0xe3, 0x49, 0x46, 0x12, 0x34, 0xe4, 0xd9, 0x4f, 0x01, 0x18, 0x50, 0xba, 0xb5, 0xc0, 0x49, 0xb6, 0x2a, 0x59, 0x43, 0x38, 0x66, 0xfc, 0xce, + 0x69, 0x66, 0x49, 0x5c, 0x26, 0x5c, 0x47, 0x65, 0xa5, 0x6c, 0x06, 0xb9, 0xfc, 0x42, 0x76, 0x54, 0x87, 0x85, 0xf4, 0x68, 0x28, 0xca, 0x60, 0x2d, 0xc6, 0xd0, 0x54, 0x1f, 0x25, 0x07, 0x89, 0xc4, + 0x9e, 0x8b, 0x06, 0x55, 0x9c, 0x43, 0x44, 0x60, 0xa8, 0x43, 0x80, 0x98, 0x54, 0xe5, 0xb4, 0x6e, 0x89, 0x38, 0x9f, 0x10, 0xf4, 0x89, 0x66, 0x74, 0x91, 0xc1, 0x93, 0x5e, 0x8a, 0xfb, 0x9e, 0xb4, + 0x71, 0x8f, 0x86, 0xac, 0x45, 0x89, 0x32, 0xbc, 0xf3, 0x3c, 0x9a, 0xbe, 0xcb, 0x2d, 0xc0, 0xc0, 0x93, 0xa7, 0xe8, 0x1d, 0xa0, 0x32, 0x7b, 0xb6, 0x37, 0x52, 0x81, 0x05, 0xc3, 0x58, 0xeb, 0x76, + 0x8d, 0x32, 0x3a, 0x37, 0xd4, 0x0a, 0x8c, 0x19, 0x9b, 0x7c, 0x4b, 0xb1, 0xd7, 0x2b, 0x72, 0xb6, 0x90, 0xb3, 0x6d, 0xd2, 0x7a, 0x93, 0x55, 0x19, 0x1b, 0x3c, 0x3a, 0xa6, 0x75, 0xa7, 0xe6, 0xf8, + 0x55, 0xeb, 0x50, 0x5f, 0x57, 0x98, 0x65, 0xdb, 0xd8, 0x91, 0x05, 0x65, 0x50, 0x5e, 0x7c, 0x0f, 0xdd, 0x54, 0x5c, 0xbb, 0xb8, 0x71, 0xb0, 0xb2, 0xcc, 0x01, 0x25, 0xb7, 0x4f, 0x6b, 0x0c, 0x9b, + 0x79, 0x67, 0x0a, 0x62, 0x02, 0xd1, 0xb9, 0x15, 0x4a, 0xc7, 0x76, 0x6b, 0x19, 0x19, 0xc4, 0x89, 0x58, 0x90, 0x86, 0xad, 0x8b, 0x45, 0xbe, 0x0d, 0x79, 0xc9, 0x76, 0xc3, 0xc3, 0x9d, 0x6b, 0x25, + 0x21, 0x3b, 0xb0, 0xb7, 0x8a, 0x57, 0x50, 0xe6, 0xa8, 0xeb, 0x34, 0x33, 0x0b, 0xb3, 0xcf, 0xf2, 0xb1, 0xc0, 0x72, 0x2a, 0xc8, 0x83, 0xb0, 0x48, 0xf4, 0xb8, 0xcd, 0x06, 0x19, 0x6d, 0xa8, 0xaa, + 0x8b, 0x05, 0xda, 0x42, 0x67, 0x55, 0x2b, 0xf8, 0x7a, 0xbc, 0xa5, 0x12, 0x4d, 0xc3, 0x58, 0xa8, 0x38, 0x10, 0x40, 0xe9, 0xb8, 0x1f, 0xb0, 0x84, 0x43, 0x15, 0x02, 0x15, 0xd6, 0x92, 0x23, 0x28, + 0x00, 0x0a, 0xc0, 0xb7, 0x88, 0xb1, 0x21, 0x93, 0x1a, 0x26, 0x7d, 0x80, 0x61, 0x9c, 0xe7, 0xd2, 0x9c, 0xd7, 0x6b, 0x60, 0xcf, 0x65, 0x83, 0xdc, 0xe8, 0xce, 0xbc, 0x49, 0x01, 0x85, 0x73, 0x6c, + 0x81, 0x8b, 0x25, 0xad, 0x26, 0x0b, 0x66, 0x7b, 0x1f, 0xfd, 0x46, 0x20, 0x6d, 0x01, 0x04, 0x55, 0x3a, 0xa9, 0xfb, 0x30, 0x45, 0x54, 0xa2, 0x1c, 0x32, 0x72, 0x44, 0xce, 0x78, 0xaf, 0xdb, 0xd3, + 0xb4, 0x62, 0x36, 0x1b, 0xb0, 0x68, 0xa1, 0x55, 0x63, 0x64, 0x09, 0xf5, 0x74, 0xc5, 0x71, 0x65, 0x72, 0xe2, 0xa5, 0xf2, 0xa4, 0xb0, 0x4f, 0xb8, 0xaa, 0xd1, 0x23, 0x66, 0x84, 0x84, 0x17, 0x87, + 0x56, 0x2a, 0xaf, 0x46, 0xc2, 0xc0, 0xda, 0x46, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, + 0x54, 0xa3, 0x16, 0x65, 0x29, 0xb5, 0x39, 0x22, 0xa5, 0x89, 0x9a, 0x0b, 0xc4, 0x65, 0xee, 0x5f, 0xc2, 0xc0, 0x41, 0x55, 0x58, 0x2a, 0x40, 0xac, 0x70, 0x97, 0x61, 0xd2, 0xbe, 0x61, 0xfd, 0xc7, + 0x6c, 0x59, 0x30, 0x44, 0xce, 0xbc, 0xc7, 0xf2, 0x86, 0x26, 0xed, 0x79, 0xd4, 0x51, 0x14, 0x08, 0x00, 0xe0, 0x3b, 0x59, 0xb9, 0x56, 0xf8, 0x21, 0x0e, 0x55, 0x60, 0x67, 0x40, 0x7d, 0x13, 0xdc, + 0x90, 0xfa, 0x9e, 0x8b, 0x87, 0x2b, 0xfb, 0x8f, 0xa0, 0x82, 0x06, 0x65, 0x03, 0x82, 0x06, 0x61, 0x00, 0xda, 0x18, 0x71, 0x2d, 0x31, 0x6e, 0x98, 0xdc, 0x7a, 0xc8, 0xc3, 0xca, 0x47, 0x37, 0x0e, + 0xbd, 0x77, 0x0c, 0xe3, 0x2b, 0x3b, 0xd4, 0xb1, 0xa0, 0xc9, 0x52, 0x9a, 0xc6, 0xec, 0x8e, 0xe0, 0x28, 0xb1, 0xcd, 0xb2, 0x65, 0x1c, 0xb5, 0xa6, 0xbb, 0x3c, 0x0c, 0x6d, 0xf1, 0x24, 0x0a, 0x3b, + 0x91, 0x4b, 0x56, 0x56, 0xc0, 0xdc, 0x51, 0xc2, 0xb9, 0x1b, 0xfc, 0xbc, 0x37, 0xa4, 0x66, 0x02, 0x87, 0xd4, 0x4f, 0x81, 0xf8, 0x53, 0xc7, 0xf4, 0x9a, 0x6d, 0x06, 0x03, 0xd6, 0xd7, 0x23, 0xcb, + 0xec, 0x01, 0x5f, 0xbc, 0x43, 0x4a, 0x38, 0x24, 0x1c, 0x10, 0x9c, 0x7e, 0xd5, 0xb1, 0xcc, 0x46, 0x1a, 0x2c, 0xcb, 0x9a, 0xb7, 0x14, 0x0f, 0x19, 0xf3, 0x7a, 0x13, 0xbb, 0x70, 0x1e, 0x14, 0x2b, + 0xd5, 0x4b, 0x64, 0xec, 0x6b, 0x76, 0xfe, 0xc3, 0x3b, 0x69, 0xc2, 0x91, 0x8c, 0xb0, 0x17, 0xc4, 0x14, 0x34, 0x23, 0x00, 0x9a, 0x3c, 0x07, 0xb5, 0xc1, 0x81, 0xb0, 0xc1, 0xeb, 0x49, 0x4a, 0x62, + 0xab, 0xc8, 0x39, 0x13, 0x97, 0x08, 0x9e, 0xa6, 0x64, 0x09, 0x67, 0xc1, 0x20, 0x49, 0x84, 0xcd, 0x48, 0x4c, 0xcc, 0xb0, 0x0a, 0x9a, 0x17, 0xd0, 0x87, 0x21, 0x84, 0x28, 0xef, 0x3b, 0xb7, 0x08, + 0x78, 0x3e, 0x12, 0x82, 0x71, 0x04, 0x41, 0x73, 0x75, 0xb6, 0x95, 0x6f, 0xb5, 0x00, 0x53, 0xd0, 0x48, 0xa4, 0x79, 0x14, 0x95, 0x82, 0x4a, 0x34, 0x80, 0xa5, 0xb7, 0x83, 0x02, 0x56, 0x09, 0x6f, + 0xdd, 0x72, 0x5c, 0x30, 0x8b, 0x3b, 0xe8, 0x4a, 0x07, 0xf3, 0x63, 0x2e, 0x24, 0x95, 0xc6, 0x2e, 0x96, 0x39, 0x9d, 0x80, 0xbf, 0xa7, 0x45, 0xb9, 0x84, 0x1a, 0x18, 0x33, 0xbc, 0x1d, 0x27, 0xba, + 0x45, 0xa5, 0x21, 0x68, 0xee, 0x59, 0x00, 0x6c, 0x3a, 0x3a, 0x8c, 0x4a, 0x5a, 0x4f, 0x50, 0x88, 0xfc, 0x73, 0x71, 0x81, 0xab, 0x51, 0x96, 0xf7, 0xb1, 0xb4, 0x9a, 0x2e, 0xd8, 0x13, 0x13, 0x4e, + 0x11, 0x2f, 0x73, 0x0b, 0x99, 0x1c, 0x54, 0xa7, 0x19, 0x6b, 0xcf, 0x5f, 0xc7, 0x6e, 0x13, 0x4c, 0x58, 0x43, 0xe1, 0x69, 0x88, 0x51, 0xb2, 0xf8, 0x69, 0xaf, 0xaf, 0xb0, 0x27, 0x87, 0xd9, 0xc2, + 0xf1, 0x36, 0x90, 0x2d, 0xc7, 0xa7, 0xf3, 0xd6, 0x21, 0x56, 0xd1, 0x5e, 0xc3, 0x09, 0x56, 0x40, 0x92, 0xc6, 0x1d, 0x83, 0xb0, 0x98, 0x6c, 0x48, 0x40, 0x99, 0x81, 0xf3, 0xc1, 0x86, 0x88, 0x0a, + 0x2f, 0x63, 0xd5, 0x86, 0x0a, 0xb6, 0x01, 0xde, 0xac, 0x2b, 0x6b, 0xa1, 0xb4, 0x28, 0x17, 0x9d, 0x73, 0x53, 0x3e, 0xb7, 0xa3, 0xa5, 0x11, 0x3b, 0x85, 0x61, 0xf1, 0x0b, 0x45, 0xc3, 0xcd, 0xe2, + 0x82, 0xb6, 0xea, 0xd6, 0xab, 0x6c, 0x60, 0x4f, 0x09, 0xc1, 0x7b, 0xfd, 0xa0, 0x83, 0x13, 0xa3, 0x26, 0x07, 0x67, 0x5a, 0xdf, 0x64, 0x31, 0xca, 0x87, 0x18, 0xe9, 0xc4, 0x3a, 0x73, 0x73, 0x32, + 0x27, 0xe7, 0x3b, 0xc6, 0x1a, 0xc8, 0x45, 0xba, 0x90, 0x77, 0x55, 0xce, 0xc6, 0x89, 0x25, 0xe5, 0xe2, 0xbf, 0xe9, 0x12, 0x95, 0x9d, 0xb8, 0x6f, 0xbf, 0xe2, 0x15, 0x6f, 0xd5, 0xbb, 0xdb, 0xf0, + 0xc9, 0xdf, 0x8b, 0x53, 0x02, 0xaa, 0x8d, 0x90, 0xa2, 0x2d, 0x12, 0x27, 0x0e, 0x00, 0x65, 0x51, 0xe4, 0x76, 0x7e, 0x45, 0x26, 0x8e, 0xd9, 0x69, 0x26, 0x54, 0x44, 0x78, 0x11, 0xea, 0xb8, 0x4f, + 0x04, 0x99, 0xa8, 0xa5, 0x8c, 0xf7, 0xc0, 0x4a, 0x59, 0x56, 0x98, 0x52, 0x80, 0x45, 0xf2, 0x98, 0x97, 0xc8, 0xfa, 0x96, 0xd0, 0x6c, 0xce, 0x51, 0xe6, 0xaf, 0xea, 0xc4, 0x33, 0x95, 0x89, 0xc9, + 0x41, 0xc8, 0x55, 0x63, 0xd7, 0x0f, 0xac, 0xe1, 0x92, 0x88, 0x94, 0xba, 0xc0, 0x36, 0x19, 0xdf, 0xf4, 0xbe, 0x3f, 0x43, 0x14, 0xa3, 0xf7, 0x35, 0x1a, 0x09, 0xa4, 0x86, 0xb5, 0x04, 0x1e, 0x7c, + 0xb2, 0xda, 0x8b, 0x96, 0xbc, 0x66, 0x26, 0xa4, 0x93, 0x17, 0x35, 0x7c, 0x41, 0x52, 0xa5, 0x1b, 0xa3, 0xc2, 0x8c, 0x7e, 0x0c, 0x9d, 0xb4, 0x1a, 0x06, 0xa2, 0x82, 0x90, 0xf2, 0x18, 0x73, 0x11, + 0x07, 0xc9, 0x54, 0xd8, 0xa6, 0x6f, 0x80, 0x1d, 0x7d, 0xe1, 0x2a, 0x03, 0x71, 0x16, 0x99, 0x0b, 0x6c, 0x53, 0xc1, 0x29, 0xf1, 0x85, 0xc3, 0x45, 0xf2, 0x7e, 0x51, 0x8b, 0x2d, 0x5a, 0x91, 0x25, + 0xa0, 0x70, 0x76, 0xd9, 0x91, 0xb7, 0xda, 0xc7, 0xcc, 0x65, 0xa8, 0x56, 0x2e, 0xfb, 0xcc, 0x32, 0xa9, 0xca, 0x4a, 0xd9, 0x02, 0x63, 0xb0, 0x4a, 0x4f, 0x90, 0x36, 0x11, 0x6c, 0x7b, 0x97, 0x48, + 0x04, 0x96, 0x31, 0x75, 0x75, 0x65, 0x0d, 0xcc, 0x21, 0x52, 0xb5, 0xbc, 0x0e, 0x74, 0x40, 0x7e, 0x12, 0xfa, 0x8e, 0x4f, 0xfc, 0xcc, 0xff, 0x76, 0xc0, 0x1a, 0x97, 0x4b, 0xd6, 0x11, 0x02, 0xe1, + 0xf5, 0x29, 0x64, 0x96, 0xc7, 0x1d, 0x07, 0x64, 0xe1, 0x32, 0x29, 0xff, 0xe7, 0x84, 0x6f, 0x33, 0x6e, 0x34, 0xca, 0xc9, 0x04, 0xca, 0x56, 0x70, 0xf8, 0xcd, 0x50, 0x52, 0x42, 0x7a, 0x79, 0xc0, + 0x91, 0xa9, 0x71, 0x21, 0x0c, 0x5c, 0xff, 0x66, 0x7a, 0xac, 0x24, 0x93, 0x66, 0xe1, 0x0d, 0x2b, 0x11, 0x37, 0x6c, 0xa3, 0x9d, 0x93, 0x52, 0x04, 0xb1, 0x2c, 0xc5, 0x85, 0xe9, 0x40, 0x54, 0x03, + 0x62, 0x5f, 0xb3, 0x2c, 0xb5, 0xe5, 0xc3, 0x1b, 0x62, 0x34, 0x81, 0x60, 0x51, 0x5c, 0xcc, 0x4f, 0xda, 0xf5, 0x70, 0x2d, 0x6b, 0xab, 0x5c, 0x37, 0x3d, 0xb6, 0xf3, 0x50, 0xd3, 0xe6, 0x3a, 0x5c, + 0xe3, 0xca, 0x54, 0x74, 0xa0, 0xcf, 0x15, 0x67, 0x04, 0x2c, 0xa3, 0x25, 0x89, 0x86, 0xff, 0x75, 0xbd, 0xfc, 0xd9, 0x29, 0xe6, 0x46, 0x2f, 0x36, 0xbc, 0xcc, 0x3f, 0x5a, 0x93, 0x35, 0x2a, 0x2b, + 0x36, 0xcb, 0x16, 0x2e, 0x18, 0x74, 0xc7, 0x42, 0x87, 0x0a, 0x97, 0xb1, 0x67, 0xa0, 0x50, 0x37, 0x36, 0x24, 0xea, 0xeb, 0x7e, 0x50, 0x73, 0x25, 0x6b, 0x72, 0x11, 0xb2, 0xd9, 0x4b, 0x84, 0x06, + 0xcd, 0x6c, 0x95, 0x33, 0xb1, 0x53, 0x64, 0x08, 0xab, 0x0a, 0x29, 0xe5, 0xb2, 0xf0, 0xc9, 0x54, 0xec, 0xe0, 0x0f, 0xbb, 0xeb, 0x17, 0x6d, 0x72, 0x4d, 0x4c, 0xf4, 0x43, 0xcf, 0x70, 0x20, 0xd5, + 0xfa, 0x70, 0x94, 0xcc, 0x1b, 0x1b, 0xe6, 0x97, 0xba, 0xd3, 0x36, 0x74, 0xe4, 0x09, 0x9e, 0xc7, 0xbb, 0x18, 0xf4, 0x57, 0x71, 0x28, 0xcd, 0xd9, 0x7c, 0xcd, 0x6d, 0x44, 0x62, 0xe5, 0x60, 0x7c, + 0x51, 0x2a, 0x3e, 0x36, 0x24, 0x8e, 0x3d, 0xda, 0xa2, 0xec, 0x08, 0x9a, 0xef, 0xc4, 0xce, 0x48, 0x5c, 0x49, 0xd7, 0xb0, 0x09, 0xc8, 0xd6, 0x31, 0x15, 0xfc, 0x81, 0xff, 0x3a, 0x62, 0xd1, 0x5a, + 0x88, 0x44, 0x1c, 0x03, 0xea, 0x1c, 0x2e, 0x72, 0xc4, 0x88, 0x39, 0xfc, 0x6a, 0xd7, 0x3a, 0x30, 0x74, 0x4a, 0x62, 0xb7, 0xb2, 0x16, 0x45, 0xa6, 0xaf, 0x7d, 0x61, 0xb6, 0x38, 0x3b, 0x22, 0x1e, + 0x21, 0x90, 0x55, 0x57, 0xcd, 0x29, 0xd9, 0x24, 0xa6, 0x09, 0x86, 0xc5, 0x11, 0xc1, 0xeb, 0xbc, 0x31, 0x6d, 0x56, 0x30, 0xa2, 0x41, 0x43, 0x23, 0xf5, 0x3a, 0xd5, 0x59, 0x94, 0xf6, 0xb3, 0x65, + 0x39, 0xf9, 0xc4, 0x40, 0x75, 0xa5, 0x33, 0xe4, 0x81, 0xc0, 0x84, 0x45, 0xd9, 0xca, 0x9e, 0x9d, 0x38, 0x21, 0x19, 0x38, 0x8b, 0xd1, 0xd7, 0x50, 0x52, 0x21, 0x7a, 0x94, 0x4c, 0xcc, 0x7b, 0xe9, + 0x09, 0xe2, 0x19, 0x71, 0x1f, 0xcc, 0x79, 0x24, 0x76, 0x92, 0x13, 0xa1, 0x92, 0x53, 0x4a, 0x55, 0x80, 0x08, 0x15, 0x7a, 0x39, 0x6e, 0xdf, 0xf4, 0x80, 0xcc, 0x3b, 0x52, 0x0f, 0xf8, 0x18, 0xb3, + 0x8b, 0x13, 0x5c, 0x18, 0xa8, 0x0d, 0x51, 0x05, 0xe6, 0x78, 0x83, 0x6c, 0x39, 0x5c, 0x28, 0xe9, 0x2f, 0x7a, 0x3c, 0x4e, 0x93, 0xc0, 0x10, 0x35, 0xf3, 0x41, 0x11, 0xcc, 0x49, 0x02, 0xd0, 0xc0, + 0x33, 0xa6, 0x3f, 0x23, 0x6a, 0x71, 0xda, 0x97, 0x4a, 0x6f, 0x40, 0x4f, 0x7a, 0xa7, 0xb5, 0xe5, 0x82, 0xc7, 0x58, 0x14, 0x2f, 0xc1, 0x82, 0x6b, 0xba, 0x98, 0xb2, 0x7d, 0x57, 0xc2, 0xe2, 0x10, + 0x3e, 0x10, 0xe3, 0x0d, 0x32, 0x79, 0x7b, 0x96, 0x77, 0x14, 0xd1, 0x56, 0x61, 0x11, 0x13, 0x71, 0xa2, 0xd9, 0xc5, 0x39, 0x98, 0x12, 0x46, 0x46, 0x22, 0x63, 0x5b, 0x44, 0x21, 0x26, 0xb0, 0x98, + 0x36, 0xb0, 0x81, 0x82, 0x72, 0x47, 0xd0, 0x54, 0x22, 0x97, 0x2b, 0xd0, 0x32, 0x0d, 0x8f, 0x42, 0xbf, 0x57, 0xe3, 0x49, 0x46, 0x12, 0x34, 0xe4, 0xd9, 0x4f, 0x01, 0x18, 0x50, 0xba, 0xb5, 0xc0, + 0x49, 0xb6, 0x2a, 0x59, 0x43, 0x38, 0x66, 0xfc, 0xce, 0x69, 0x66, 0x49, 0x5c, 0x26, 0x5c, 0x47, 0x65, 0xa5, 0x6c, 0x06, 0xb9, 0xfc, 0x42, 0x76, 0x54, 0x87, 0x85, 0xf4, 0x68, 0x28, 0xca, 0x60, + 0x2d, 0xc6, 0xd0, 0x54, 0x1f, 0x25, 0x07, 0x89, 0xc4, 0x9e, 0x8b, 0x06, 0x55, 0x9c, 0x43, 0x44, 0x60, 0xa8, 0x43, 0x80, 0x98, 0x54, 0xe5, 0xb4, 0x6e, 0x89, 0x38, 0x9f, 0x10, 0xf4, 0x89, 0x66, + 0x74, 0x91, 0xc1, 0x93, 0x5e, 0x8a, 0xfb, 0x9e, 0xb4, 0x71, 0x8f, 0x86, 0xac, 0x45, 0x89, 0x32, 0xbc, 0xf3, 0x3c, 0x9a, 0xbe, 0xcb, 0x2d, 0xc0, 0xc0, 0x93, 0xa7, 0xe8, 0x1d, 0xa0, 0x32, 0x7b, + 0xb6, 0x37, 0x52, 0x81, 0x05, 0xc3, 0x58, 0xeb, 0x76, 0x8d, 0x32, 0x3a, 0x37, 0xd4, 0x0a, 0x8c, 0x19, 0x9b, 0x7c, 0x4b, 0xb1, 0xd7, 0x2b, 0x72, 0xb6, 0x90, 0xb3, 0x6d, 0xd2, 0x7a, 0x93, 0x55, + 0x19, 0x1b, 0x3c, 0x3a, 0xa6, 0x75, 0xa7, 0xe6, 0xf8, 0x55, 0xeb, 0x50, 0x5f, 0x57, 0x98, 0x65, 0xdb, 0xd8, 0x91, 0x05, 0x65, 0x50, 0x5e, 0x7c, 0x0f, 0xdd, 0x54, 0x5c, 0xbb, 0xb8, 0x71, 0xb0, + 0xb2, 0xcc, 0x01, 0x25, 0xb7, 0x4f, 0x6b, 0x0c, 0x9b, 0x79, 0x67, 0x0a, 0x62, 0x02, 0xd1, 0xb9, 0x15, 0x4a, 0xc7, 0x76, 0x6b, 0x19, 0x19, 0xc4, 0x89, 0x58, 0x90, 0x86, 0xad, 0x8b, 0x45, 0xbe, + 0x0d, 0x79, 0xc9, 0x76, 0xc3, 0xc3, 0x9d, 0x6b, 0x25, 0x21, 0x3b, 0xb0, 0xb7, 0x8a, 0x57, 0x50, 0xe6, 0xa8, 0xeb, 0x34, 0x33, 0x0b, 0xb3, 0xcf, 0xf2, 0xb1, 0xc0, 0x72, 0x2a, 0xc8, 0x83, 0xb0, + 0x48, 0xf4, 0xb8, 0xcd, 0x06, 0x19, 0x6d, 0xa8, 0xaa, 0x8b, 0x05, 0xda, 0x42, 0x67, 0x55, 0x2b, 0xf8, 0x7a, 0xbc, 0xa5, 0x12, 0x4d, 0xc3, 0x58, 0xa8, 0x38, 0x10, 0x40, 0xe9, 0xb8, 0x1f, 0xb0, + 0x84, 0x43, 0x15, 0x02, 0x15, 0xd6, 0x92, 0x23, 0x28, 0x00, 0x0a, 0xc0, 0xb7, 0x88, 0xb1, 0x21, 0x93, 0x1a, 0x26, 0x7d, 0x80, 0x61, 0x9c, 0xe7, 0xd2, 0x9c, 0xd7, 0x6b, 0x60, 0xcf, 0x65, 0x83, + 0xdc, 0xe8, 0xce, 0xbc, 0x49, 0x01, 0x85, 0x73, 0x6c, 0x81, 0x8b, 0x25, 0xad, 0x26, 0x0b, 0x66, 0x7b, 0x1f, 0xfd, 0x46, 0x20, 0x6d, 0x01, 0x04, 0x55, 0x3a, 0xa9, 0xfb, 0x30, 0x45, 0x54, 0xa2, + 0x1c, 0x32, 0x72, 0x44, 0xce, 0x78, 0xaf, 0xdb, 0xd3, 0xb4, 0x62, 0x36, 0x1b, 0xb0, 0x68, 0xa1, 0x55, 0x63, 0x64, 0x09, 0xf5, 0x74, 0xc5, 0x71, 0x65, 0x72, 0xe2, 0xa5, 0xf2, 0xa4, 0xb0, 0x4f, + 0xb8, 0xaa, 0xd1, 0x23, 0x66, 0x84, 0x84, 0x17, 0x87, 0x56, 0x2a, 0xaf, 0x46, 0xc2, 0xc0, 0xda, 0x46, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, + 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, 0x54, 0xa3, 0x16, 0x65, 0x29, 0xb5, 0x39, 0x22, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, 0x30, + }, + .spki_len = 1603, + .spki = { + 0x30, 0x82, 0x06, 0x3f, 0x30, 0x0f, 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, 0x02, 0x82, 0x0b, 0x05, 0x04, 0x04, 0x05, 0x00, 0x03, 0x82, 0x06, 0x2a, 0x00, 0x30, 0x82, 0x06, 0x25, 0x03, 0x82, + 0x06, 0x21, 0x00, 0xda, 0x18, 0x71, 0x2d, 0x31, 0x6e, 0x98, 0xdc, 0x7a, 0xc8, 0xc3, 0xca, 0x47, 0x37, 0x0e, 0xbd, 0x77, 0x0c, 0xe3, 0x2b, 0x3b, 0xd4, 0xb1, 0xa0, 0xc9, 0x52, 0x9a, 0xc6, 0xec, + 0x8e, 0xe0, 0x28, 0xb1, 0xcd, 0xb2, 0x65, 0x1c, 0xb5, 0xa6, 0xbb, 0x3c, 0x0c, 0x6d, 0xf1, 0x24, 0x0a, 0x3b, 0x91, 0x4b, 0x56, 0x56, 0xc0, 0xdc, 0x51, 0xc2, 0xb9, 0x1b, 0xfc, 0xbc, 0x37, 0xa4, + 0x66, 0x02, 0x87, 0xd4, 0x4f, 0x81, 0xf8, 0x53, 0xc7, 0xf4, 0x9a, 0x6d, 0x06, 0x03, 0xd6, 0xd7, 0x23, 0xcb, 0xec, 0x01, 0x5f, 0xbc, 0x43, 0x4a, 0x38, 0x24, 0x1c, 0x10, 0x9c, 0x7e, 0xd5, 0xb1, + 0xcc, 0x46, 0x1a, 0x2c, 0xcb, 0x9a, 0xb7, 0x14, 0x0f, 0x19, 0xf3, 0x7a, 0x13, 0xbb, 0x70, 0x1e, 0x14, 0x2b, 0xd5, 0x4b, 0x64, 0xec, 0x6b, 0x76, 0xfe, 0xc3, 0x3b, 0x69, 0xc2, 0x91, 0x8c, 0xb0, + 0x17, 0xc4, 0x14, 0x34, 0x23, 0x00, 0x9a, 0x3c, 0x07, 0xb5, 0xc1, 0x81, 0xb0, 0xc1, 0xeb, 0x49, 0x4a, 0x62, 0xab, 0xc8, 0x39, 0x13, 0x97, 0x08, 0x9e, 0xa6, 0x64, 0x09, 0x67, 0xc1, 0x20, 0x49, + 0x84, 0xcd, 0x48, 0x4c, 0xcc, 0xb0, 0x0a, 0x9a, 0x17, 0xd0, 0x87, 0x21, 0x84, 0x28, 0xef, 0x3b, 0xb7, 0x08, 0x78, 0x3e, 0x12, 0x82, 0x71, 0x04, 0x41, 0x73, 0x75, 0xb6, 0x95, 0x6f, 0xb5, 0x00, + 0x53, 0xd0, 0x48, 0xa4, 0x79, 0x14, 0x95, 0x82, 0x4a, 0x34, 0x80, 0xa5, 0xb7, 0x83, 0x02, 0x56, 0x09, 0x6f, 0xdd, 0x72, 0x5c, 0x30, 0x8b, 0x3b, 0xe8, 0x4a, 0x07, 0xf3, 0x63, 0x2e, 0x24, 0x95, + 0xc6, 0x2e, 0x96, 0x39, 0x9d, 0x80, 0xbf, 0xa7, 0x45, 0xb9, 0x84, 0x1a, 0x18, 0x33, 0xbc, 0x1d, 0x27, 0xba, 0x45, 0xa5, 0x21, 0x68, 0xee, 0x59, 0x00, 0x6c, 0x3a, 0x3a, 0x8c, 0x4a, 0x5a, 0x4f, + 0x50, 0x88, 0xfc, 0x73, 0x71, 0x81, 0xab, 0x51, 0x96, 0xf7, 0xb1, 0xb4, 0x9a, 0x2e, 0xd8, 0x13, 0x13, 0x4e, 0x11, 0x2f, 0x73, 0x0b, 0x99, 0x1c, 0x54, 0xa7, 0x19, 0x6b, 0xcf, 0x5f, 0xc7, 0x6e, + 0x13, 0x4c, 0x58, 0x43, 0xe1, 0x69, 0x88, 0x51, 0xb2, 0xf8, 0x69, 0xaf, 0xaf, 0xb0, 0x27, 0x87, 0xd9, 0xc2, 0xf1, 0x36, 0x90, 0x2d, 0xc7, 0xa7, 0xf3, 0xd6, 0x21, 0x56, 0xd1, 0x5e, 0xc3, 0x09, + 0x56, 0x40, 0x92, 0xc6, 0x1d, 0x83, 0xb0, 0x98, 0x6c, 0x48, 0x40, 0x99, 0x81, 0xf3, 0xc1, 0x86, 0x88, 0x0a, 0x2f, 0x63, 0xd5, 0x86, 0x0a, 0xb6, 0x01, 0xde, 0xac, 0x2b, 0x6b, 0xa1, 0xb4, 0x28, + 0x17, 0x9d, 0x73, 0x53, 0x3e, 0xb7, 0xa3, 0xa5, 0x11, 0x3b, 0x85, 0x61, 0xf1, 0x0b, 0x45, 0xc3, 0xcd, 0xe2, 0x82, 0xb6, 0xea, 0xd6, 0xab, 0x6c, 0x60, 0x4f, 0x09, 0xc1, 0x7b, 0xfd, 0xa0, 0x83, + 0x13, 0xa3, 0x26, 0x07, 0x67, 0x5a, 0xdf, 0x64, 0x31, 0xca, 0x87, 0x18, 0xe9, 0xc4, 0x3a, 0x73, 0x73, 0x32, 0x27, 0xe7, 0x3b, 0xc6, 0x1a, 0xc8, 0x45, 0xba, 0x90, 0x77, 0x55, 0xce, 0xc6, 0x89, + 0x25, 0xe5, 0xe2, 0xbf, 0xe9, 0x12, 0x95, 0x9d, 0xb8, 0x6f, 0xbf, 0xe2, 0x15, 0x6f, 0xd5, 0xbb, 0xdb, 0xf0, 0xc9, 0xdf, 0x8b, 0x53, 0x02, 0xaa, 0x8d, 0x90, 0xa2, 0x2d, 0x12, 0x27, 0x0e, 0x00, + 0x65, 0x51, 0xe4, 0x76, 0x7e, 0x45, 0x26, 0x8e, 0xd9, 0x69, 0x26, 0x54, 0x44, 0x78, 0x11, 0xea, 0xb8, 0x4f, 0x04, 0x99, 0xa8, 0xa5, 0x8c, 0xf7, 0xc0, 0x4a, 0x59, 0x56, 0x98, 0x52, 0x80, 0x45, + 0xf2, 0x98, 0x97, 0xc8, 0xfa, 0x96, 0xd0, 0x6c, 0xce, 0x51, 0xe6, 0xaf, 0xea, 0xc4, 0x33, 0x95, 0x89, 0xc9, 0x41, 0xc8, 0x55, 0x63, 0xd7, 0x0f, 0xac, 0xe1, 0x92, 0x88, 0x94, 0xba, 0xc0, 0x36, + 0x19, 0xdf, 0xf4, 0xbe, 0x3f, 0x43, 0x14, 0xa3, 0xf7, 0x35, 0x1a, 0x09, 0xa4, 0x86, 0xb5, 0x04, 0x1e, 0x7c, 0xb2, 0xda, 0x8b, 0x96, 0xbc, 0x66, 0x26, 0xa4, 0x93, 0x17, 0x35, 0x7c, 0x41, 0x52, + 0xa5, 0x1b, 0xa3, 0xc2, 0x8c, 0x7e, 0x0c, 0x9d, 0xb4, 0x1a, 0x06, 0xa2, 0x82, 0x90, 0xf2, 0x18, 0x73, 0x11, 0x07, 0xc9, 0x54, 0xd8, 0xa6, 0x6f, 0x80, 0x1d, 0x7d, 0xe1, 0x2a, 0x03, 0x71, 0x16, + 0x99, 0x0b, 0x6c, 0x53, 0xc1, 0x29, 0xf1, 0x85, 0xc3, 0x45, 0xf2, 0x7e, 0x51, 0x8b, 0x2d, 0x5a, 0x91, 0x25, 0xa0, 0x70, 0x76, 0xd9, 0x91, 0xb7, 0xda, 0xc7, 0xcc, 0x65, 0xa8, 0x56, 0x2e, 0xfb, + 0xcc, 0x32, 0xa9, 0xca, 0x4a, 0xd9, 0x02, 0x63, 0xb0, 0x4a, 0x4f, 0x90, 0x36, 0x11, 0x6c, 0x7b, 0x97, 0x48, 0x04, 0x96, 0x31, 0x75, 0x75, 0x65, 0x0d, 0xcc, 0x21, 0x52, 0xb5, 0xbc, 0x0e, 0x74, + 0x40, 0x7e, 0x12, 0xfa, 0x8e, 0x4f, 0xfc, 0xcc, 0xff, 0x76, 0xc0, 0x1a, 0x97, 0x4b, 0xd6, 0x11, 0x02, 0xe1, 0xf5, 0x29, 0x64, 0x96, 0xc7, 0x1d, 0x07, 0x64, 0xe1, 0x32, 0x29, 0xff, 0xe7, 0x84, + 0x6f, 0x33, 0x6e, 0x34, 0xca, 0xc9, 0x04, 0xca, 0x56, 0x70, 0xf8, 0xcd, 0x50, 0x52, 0x42, 0x7a, 0x79, 0xc0, 0x91, 0xa9, 0x71, 0x21, 0x0c, 0x5c, 0xff, 0x66, 0x7a, 0xac, 0x24, 0x93, 0x66, 0xe1, + 0x0d, 0x2b, 0x11, 0x37, 0x6c, 0xa3, 0x9d, 0x93, 0x52, 0x04, 0xb1, 0x2c, 0xc5, 0x85, 0xe9, 0x40, 0x54, 0x03, 0x62, 0x5f, 0xb3, 0x2c, 0xb5, 0xe5, 0xc3, 0x1b, 0x62, 0x34, 0x81, 0x60, 0x51, 0x5c, + 0xcc, 0x4f, 0xda, 0xf5, 0x70, 0x2d, 0x6b, 0xab, 0x5c, 0x37, 0x3d, 0xb6, 0xf3, 0x50, 0xd3, 0xe6, 0x3a, 0x5c, 0xe3, 0xca, 0x54, 0x74, 0xa0, 0xcf, 0x15, 0x67, 0x04, 0x2c, 0xa3, 0x25, 0x89, 0x86, + 0xff, 0x75, 0xbd, 0xfc, 0xd9, 0x29, 0xe6, 0x46, 0x2f, 0x36, 0xbc, 0xcc, 0x3f, 0x5a, 0x93, 0x35, 0x2a, 0x2b, 0x36, 0xcb, 0x16, 0x2e, 0x18, 0x74, 0xc7, 0x42, 0x87, 0x0a, 0x97, 0xb1, 0x67, 0xa0, + 0x50, 0x37, 0x36, 0x24, 0xea, 0xeb, 0x7e, 0x50, 0x73, 0x25, 0x6b, 0x72, 0x11, 0xb2, 0xd9, 0x4b, 0x84, 0x06, 0xcd, 0x6c, 0x95, 0x33, 0xb1, 0x53, 0x64, 0x08, 0xab, 0x0a, 0x29, 0xe5, 0xb2, 0xf0, + 0xc9, 0x54, 0xec, 0xe0, 0x0f, 0xbb, 0xeb, 0x17, 0x6d, 0x72, 0x4d, 0x4c, 0xf4, 0x43, 0xcf, 0x70, 0x20, 0xd5, 0xfa, 0x70, 0x94, 0xcc, 0x1b, 0x1b, 0xe6, 0x97, 0xba, 0xd3, 0x36, 0x74, 0xe4, 0x09, + 0x9e, 0xc7, 0xbb, 0x18, 0xf4, 0x57, 0x71, 0x28, 0xcd, 0xd9, 0x7c, 0xcd, 0x6d, 0x44, 0x62, 0xe5, 0x60, 0x7c, 0x51, 0x2a, 0x3e, 0x36, 0x24, 0x8e, 0x3d, 0xda, 0xa2, 0xec, 0x08, 0x9a, 0xef, 0xc4, + 0xce, 0x48, 0x5c, 0x49, 0xd7, 0xb0, 0x09, 0xc8, 0xd6, 0x31, 0x15, 0xfc, 0x81, 0xff, 0x3a, 0x62, 0xd1, 0x5a, 0x88, 0x44, 0x1c, 0x03, 0xea, 0x1c, 0x2e, 0x72, 0xc4, 0x88, 0x39, 0xfc, 0x6a, 0xd7, + 0x3a, 0x30, 0x74, 0x4a, 0x62, 0xb7, 0xb2, 0x16, 0x45, 0xa6, 0xaf, 0x7d, 0x61, 0xb6, 0x38, 0x3b, 0x22, 0x1e, 0x21, 0x90, 0x55, 0x57, 0xcd, 0x29, 0xd9, 0x24, 0xa6, 0x09, 0x86, 0xc5, 0x11, 0xc1, + 0xeb, 0xbc, 0x31, 0x6d, 0x56, 0x30, 0xa2, 0x41, 0x43, 0x23, 0xf5, 0x3a, 0xd5, 0x59, 0x94, 0xf6, 0xb3, 0x65, 0x39, 0xf9, 0xc4, 0x40, 0x75, 0xa5, 0x33, 0xe4, 0x81, 0xc0, 0x84, 0x45, 0xd9, 0xca, + 0x9e, 0x9d, 0x38, 0x21, 0x19, 0x38, 0x8b, 0xd1, 0xd7, 0x50, 0x52, 0x21, 0x7a, 0x94, 0x4c, 0xcc, 0x7b, 0xe9, 0x09, 0xe2, 0x19, 0x71, 0x1f, 0xcc, 0x79, 0x24, 0x76, 0x92, 0x13, 0xa1, 0x92, 0x53, + 0x4a, 0x55, 0x80, 0x08, 0x15, 0x7a, 0x39, 0x6e, 0xdf, 0xf4, 0x80, 0xcc, 0x3b, 0x52, 0x0f, 0xf8, 0x18, 0xb3, 0x8b, 0x13, 0x5c, 0x18, 0xa8, 0x0d, 0x51, 0x05, 0xe6, 0x78, 0x83, 0x6c, 0x39, 0x5c, + 0x28, 0xe9, 0x2f, 0x7a, 0x3c, 0x4e, 0x93, 0xc0, 0x10, 0x35, 0xf3, 0x41, 0x11, 0xcc, 0x49, 0x02, 0xd0, 0xc0, 0x33, 0xa6, 0x3f, 0x23, 0x6a, 0x71, 0xda, 0x97, 0x4a, 0x6f, 0x40, 0x4f, 0x7a, 0xa7, + 0xb5, 0xe5, 0x82, 0xc7, 0x58, 0x14, 0x2f, 0xc1, 0x82, 0x6b, 0xba, 0x98, 0xb2, 0x7d, 0x57, 0xc2, 0xe2, 0x10, 0x3e, 0x10, 0xe3, 0x0d, 0x32, 0x79, 0x7b, 0x96, 0x77, 0x14, 0xd1, 0x56, 0x61, 0x11, + 0x13, 0x71, 0xa2, 0xd9, 0xc5, 0x39, 0x98, 0x12, 0x46, 0x46, 0x22, 0x63, 0x5b, 0x44, 0x21, 0x26, 0xb0, 0x98, 0x36, 0xb0, 0x81, 0x82, 0x72, 0x47, 0xd0, 0x54, 0x22, 0x97, 0x2b, 0xd0, 0x32, 0x0d, + 0x8f, 0x42, 0xbf, 0x57, 0xe3, 0x49, 0x46, 0x12, 0x34, 0xe4, 0xd9, 0x4f, 0x01, 0x18, 0x50, 0xba, 0xb5, 0xc0, 0x49, 0xb6, 0x2a, 0x59, 0x43, 0x38, 0x66, 0xfc, 0xce, 0x69, 0x66, 0x49, 0x5c, 0x26, + 0x5c, 0x47, 0x65, 0xa5, 0x6c, 0x06, 0xb9, 0xfc, 0x42, 0x76, 0x54, 0x87, 0x85, 0xf4, 0x68, 0x28, 0xca, 0x60, 0x2d, 0xc6, 0xd0, 0x54, 0x1f, 0x25, 0x07, 0x89, 0xc4, 0x9e, 0x8b, 0x06, 0x55, 0x9c, + 0x43, 0x44, 0x60, 0xa8, 0x43, 0x80, 0x98, 0x54, 0xe5, 0xb4, 0x6e, 0x89, 0x38, 0x9f, 0x10, 0xf4, 0x89, 0x66, 0x74, 0x91, 0xc1, 0x93, 0x5e, 0x8a, 0xfb, 0x9e, 0xb4, 0x71, 0x8f, 0x86, 0xac, 0x45, + 0x89, 0x32, 0xbc, 0xf3, 0x3c, 0x9a, 0xbe, 0xcb, 0x2d, 0xc0, 0xc0, 0x93, 0xa7, 0xe8, 0x1d, 0xa0, 0x32, 0x7b, 0xb6, 0x37, 0x52, 0x81, 0x05, 0xc3, 0x58, 0xeb, 0x76, 0x8d, 0x32, 0x3a, 0x37, 0xd4, + 0x0a, 0x8c, 0x19, 0x9b, 0x7c, 0x4b, 0xb1, 0xd7, 0x2b, 0x72, 0xb6, 0x90, 0xb3, 0x6d, 0xd2, 0x7a, 0x93, 0x55, 0x19, 0x1b, 0x3c, 0x3a, 0xa6, 0x75, 0xa7, 0xe6, 0xf8, 0x55, 0xeb, 0x50, 0x5f, 0x57, + 0x98, 0x65, 0xdb, 0xd8, 0x91, 0x05, 0x65, 0x50, 0x5e, 0x7c, 0x0f, 0xdd, 0x54, 0x5c, 0xbb, 0xb8, 0x71, 0xb0, 0xb2, 0xcc, 0x01, 0x25, 0xb7, 0x4f, 0x6b, 0x0c, 0x9b, 0x79, 0x67, 0x0a, 0x62, 0x02, + 0xd1, 0xb9, 0x15, 0x4a, 0xc7, 0x76, 0x6b, 0x19, 0x19, 0xc4, 0x89, 0x58, 0x90, 0x86, 0xad, 0x8b, 0x45, 0xbe, 0x0d, 0x79, 0xc9, 0x76, 0xc3, 0xc3, 0x9d, 0x6b, 0x25, 0x21, 0x3b, 0xb0, 0xb7, 0x8a, + 0x57, 0x50, 0xe6, 0xa8, 0xeb, 0x34, 0x33, 0x0b, 0xb3, 0xcf, 0xf2, 0xb1, 0xc0, 0x72, 0x2a, 0xc8, 0x83, 0xb0, 0x48, 0xf4, 0xb8, 0xcd, 0x06, 0x19, 0x6d, 0xa8, 0xaa, 0x8b, 0x05, 0xda, 0x42, 0x67, + 0x55, 0x2b, 0xf8, 0x7a, 0xbc, 0xa5, 0x12, 0x4d, 0xc3, 0x58, 0xa8, 0x38, 0x10, 0x40, 0xe9, 0xb8, 0x1f, 0xb0, 0x84, 0x43, 0x15, 0x02, 0x15, 0xd6, 0x92, 0x23, 0x28, 0x00, 0x0a, 0xc0, 0xb7, 0x88, + 0xb1, 0x21, 0x93, 0x1a, 0x26, 0x7d, 0x80, 0x61, 0x9c, 0xe7, 0xd2, 0x9c, 0xd7, 0x6b, 0x60, 0xcf, 0x65, 0x83, 0xdc, 0xe8, 0xce, 0xbc, 0x49, 0x01, 0x85, 0x73, 0x6c, 0x81, 0x8b, 0x25, 0xad, 0x26, + 0x0b, 0x66, 0x7b, 0x1f, 0xfd, 0x46, 0x20, 0x6d, 0x01, 0x04, 0x55, 0x3a, 0xa9, 0xfb, 0x30, 0x45, 0x54, 0xa2, 0x1c, 0x32, 0x72, 0x44, 0xce, 0x78, 0xaf, 0xdb, 0xd3, 0xb4, 0x62, 0x36, 0x1b, 0xb0, + 0x68, 0xa1, 0x55, 0x63, 0x64, 0x09, 0xf5, 0x74, 0xc5, 0x71, 0x65, 0x72, 0xe2, 0xa5, 0xf2, 0xa4, 0xb0, 0x4f, 0xb8, 0xaa, 0xd1, 0x23, 0x66, 0x84, 0x84, 0x17, 0x87, 0x56, 0x2a, 0xaf, 0x46, 0xc2, + 0xc0, 0xda, 0x46, 0x65, 0xea, 0xfd, 0x46, 0x5f, 0xc6, 0x4a, 0x0c, 0x5f, 0x8f, 0x3f, 0x90, 0x03, 0x48, 0x94, 0x15, 0x89, 0x9d, 0x59, 0xa5, 0x43, 0xd8, 0x20, 0x8c, 0x54, 0xa3, 0x16, 0x65, 0x29, + 0xb5, 0x39, 0x22, + }, + .secret_len = 32, + .secret = { + 0xfb, 0xc4, 0xee, 0xa6, 0x91, 0xee, 0xf4, 0xc1, 0xb4, 0x76, 0xa2, 0x99, 0x36, 0x45, 0x3f, 0x4c, 0x3d, 0x48, 0x81, 0x79, 0x4e, 0xe3, 0x7b, 0xaf, 0x0f, 0xd7, 0x28, 0x40, 0x74, 0x3e, 0x7b, 0x7d, + }, + .cipher_len = 1568, + .cipher = { + 0xc2, 0x7f, 0x01, 0x24, 0x4d, 0x4b, 0x3f, 0xb2, 0x1d, 0x84, 0x37, 0xf8, 0x40, 0x01, 0x7c, 0xcc, 0xb7, 0xb7, 0xda, 0xd5, 0xfb, 0x2b, 0x47, 0xb9, 0xb5, 0x7e, 0xae, 0x4f, 0x77, 0xd0, 0xa4, 0x55, + 0x5e, 0x50, 0x92, 0xa2, 0x49, 0x69, 0xf2, 0x27, 0x3e, 0x97, 0x02, 0x88, 0x4a, 0x08, 0x47, 0x7b, 0x56, 0x8d, 0x80, 0x17, 0xf1, 0x38, 0x75, 0xd1, 0xf5, 0xa6, 0xd4, 0x13, 0xbd, 0xd2, 0x28, 0xeb, + 0xb1, 0x12, 0x60, 0xf7, 0xf4, 0x52, 0x9c, 0xbc, 0xeb, 0xf9, 0xb6, 0x86, 0x2e, 0x8a, 0x84, 0x12, 0x35, 0xf2, 0x9f, 0x60, 0xf8, 0xe8, 0x41, 0x74, 0x34, 0x18, 0x9d, 0x57, 0x99, 0x20, 0xfe, 0x6b, + 0x98, 0xdb, 0xe7, 0x13, 0xec, 0x16, 0xc3, 0xfd, 0xdb, 0xb8, 0x1e, 0x73, 0x1d, 0x95, 0x6b, 0x06, 0xdb, 0x49, 0x80, 0xf4, 0x9c, 0x26, 0xf2, 0x86, 0x61, 0xff, 0x9c, 0xe6, 0xe9, 0xd8, 0x61, 0xec, + 0x7a, 0x09, 0x84, 0x0c, 0x19, 0xde, 0x0e, 0xb6, 0x72, 0x20, 0x71, 0xf8, 0xaa, 0x48, 0x36, 0x2d, 0x2f, 0xf1, 0x27, 0xa4, 0xae, 0x46, 0xf9, 0x93, 0x37, 0x82, 0x68, 0x32, 0xad, 0xac, 0x23, 0x91, + 0x65, 0xf2, 0x25, 0x85, 0xbb, 0x57, 0xa8, 0x89, 0xc9, 0xc6, 0xaf, 0x82, 0x36, 0x7e, 0xc7, 0xb0, 0x72, 0x37, 0xc0, 0x53, 0x5b, 0x31, 0xb3, 0x8c, 0x1c, 0xac, 0x40, 0xac, 0x1a, 0x0c, 0x95, 0x8a, + 0x18, 0x87, 0xfe, 0x34, 0x71, 0x10, 0x83, 0xfd, 0x37, 0xaf, 0x4b, 0xc5, 0xb1, 0xb4, 0xe1, 0xe2, 0xee, 0x28, 0x43, 0x69, 0x3d, 0x57, 0xdd, 0x1e, 0x65, 0x7d, 0x4c, 0x24, 0xed, 0x20, 0x7e, 0xe7, + 0x12, 0xad, 0x2a, 0x08, 0x91, 0x45, 0x81, 0x80, 0xe9, 0xe8, 0xbd, 0x36, 0xfc, 0x14, 0xd8, 0xd6, 0x33, 0xf5, 0xb7, 0x41, 0xce, 0xa1, 0x08, 0xd2, 0xd4, 0xfd, 0x75, 0x1c, 0x5a, 0x67, 0xb0, 0x5e, + 0x30, 0x32, 0x4a, 0x67, 0xe9, 0xdd, 0x75, 0xc9, 0x93, 0xd4, 0xfe, 0x08, 0x54, 0xfb, 0x78, 0xdf, 0x6f, 0x3d, 0x45, 0xa2, 0xa9, 0xc8, 0xe4, 0x25, 0x10, 0xf0, 0xc3, 0xd8, 0x02, 0x03, 0x71, 0x2f, + 0xb3, 0x9e, 0x36, 0xb5, 0xdd, 0x8b, 0x5c, 0xcd, 0x3d, 0x09, 0xce, 0xa9, 0x42, 0x03, 0xba, 0xf8, 0x72, 0x08, 0x45, 0x71, 0xec, 0xf9, 0x78, 0xbd, 0xb9, 0x54, 0x8a, 0x25, 0x0e, 0xe4, 0x90, 0x7b, + 0x4a, 0xfc, 0x31, 0xb2, 0x1f, 0x31, 0x9a, 0xe4, 0xbf, 0x0a, 0xb1, 0x9c, 0xbd, 0x11, 0xeb, 0xe1, 0x33, 0x59, 0xd1, 0xaa, 0xf4, 0xfd, 0xb8, 0x3b, 0x65, 0x02, 0x50, 0x14, 0x22, 0xa5, 0xfe, 0x50, + 0xa8, 0xa3, 0x8e, 0xf5, 0x3d, 0xeb, 0x60, 0x3c, 0xe2, 0x3f, 0xd9, 0x79, 0x2b, 0x04, 0xde, 0xb3, 0x78, 0x71, 0x9a, 0xb7, 0x69, 0xaa, 0x58, 0x97, 0xcc, 0x65, 0xe9, 0xb1, 0x63, 0x04, 0xce, 0xa5, + 0x37, 0xe1, 0x76, 0x2b, 0xd8, 0xc9, 0xb1, 0x09, 0xda, 0x14, 0xa8, 0x29, 0xe6, 0x41, 0x9f, 0x1b, 0x9f, 0xf8, 0xa4, 0x66, 0xe2, 0xa6, 0xd6, 0xb3, 0x4d, 0x74, 0xff, 0xe1, 0xa5, 0x92, 0x99, 0x18, + 0x17, 0x59, 0xd0, 0xd3, 0x87, 0xfc, 0xed, 0x1d, 0x90, 0x7f, 0x5f, 0xb5, 0xed, 0xb4, 0x26, 0xc0, 0x51, 0x30, 0xe6, 0xca, 0x59, 0x09, 0xb2, 0x76, 0xd1, 0xa4, 0x7e, 0x71, 0x3c, 0x30, 0xd9, 0x96, + 0xda, 0x5e, 0x8e, 0x57, 0xe7, 0x12, 0xc7, 0x77, 0x38, 0xf2, 0x1b, 0xe7, 0x4b, 0x42, 0xb5, 0x18, 0x43, 0x2d, 0xad, 0x7e, 0xf7, 0x3e, 0x6a, 0x8c, 0x43, 0xaa, 0x9a, 0x62, 0x69, 0x94, 0xd7, 0x1a, + 0x31, 0x81, 0x28, 0x51, 0x80, 0x6e, 0x9f, 0xbb, 0x1f, 0x2b, 0xd3, 0x56, 0xce, 0xa3, 0x9d, 0x95, 0xf2, 0xf8, 0x7c, 0xa3, 0x0d, 0xaf, 0x6f, 0x27, 0x33, 0xf7, 0xbc, 0xe7, 0x9f, 0x8d, 0xa9, 0x95, + 0x05, 0x1e, 0x49, 0xa7, 0xfd, 0x22, 0x64, 0x37, 0x9c, 0x0a, 0x75, 0x2e, 0x55, 0x3e, 0xd6, 0x08, 0xeb, 0x93, 0x44, 0xc7, 0x94, 0x98, 0xf6, 0x91, 0x53, 0x85, 0x64, 0xc5, 0x4f, 0x82, 0x3b, 0xb7, + 0x0b, 0x12, 0xb5, 0x9e, 0x88, 0x24, 0xb4, 0xa4, 0xbb, 0x1e, 0xea, 0xc6, 0x7c, 0x81, 0x0c, 0xcc, 0x2e, 0x23, 0x74, 0x47, 0x83, 0xce, 0x95, 0x80, 0x97, 0xf7, 0xa6, 0xbc, 0x6e, 0x1f, 0x17, 0x59, + 0x75, 0x21, 0xb8, 0xc3, 0xd1, 0xee, 0x85, 0x96, 0xa2, 0x9f, 0xfe, 0xf1, 0x4e, 0xd9, 0x16, 0x32, 0x09, 0x7c, 0x16, 0xd5, 0x06, 0x5d, 0xb2, 0xa9, 0x63, 0xca, 0x73, 0x83, 0xac, 0x60, 0xad, 0x8f, + 0x4e, 0xd0, 0xd4, 0x1b, 0xd0, 0xbc, 0x3b, 0xaf, 0x19, 0x8c, 0x51, 0x25, 0xae, 0x91, 0x15, 0x06, 0xc9, 0x26, 0xd4, 0xc1, 0x17, 0x85, 0xfd, 0x61, 0x82, 0x29, 0xbf, 0xf5, 0x4c, 0xb1, 0x16, 0x1a, + 0xb8, 0xfc, 0x7b, 0x51, 0xda, 0xec, 0xcc, 0xd9, 0x13, 0x1e, 0xdf, 0x43, 0x7d, 0x8e, 0x52, 0x8e, 0x75, 0x81, 0xb8, 0x2c, 0x66, 0x0e, 0x8c, 0x5e, 0x25, 0x12, 0xd5, 0xf6, 0x38, 0x0a, 0x52, 0x8f, + 0x2a, 0xe4, 0xae, 0xe2, 0x63, 0xdb, 0x96, 0x76, 0x02, 0x4b, 0xc7, 0xad, 0x39, 0x8b, 0xc9, 0xcd, 0xda, 0xd6, 0x07, 0x96, 0x8b, 0xba, 0xb2, 0x23, 0x29, 0xe0, 0x4d, 0x6e, 0x77, 0x1f, 0xe6, 0x47, + 0x10, 0x7a, 0xc4, 0x66, 0x67, 0xa5, 0x1a, 0xd5, 0x58, 0xa6, 0x35, 0xf0, 0x26, 0x95, 0x1f, 0x4f, 0x48, 0xc8, 0x88, 0xd7, 0x01, 0xc2, 0xaf, 0xf4, 0xea, 0xb4, 0xe3, 0x4a, 0xdb, 0x15, 0x9a, 0xbb, + 0xbf, 0xab, 0xe5, 0x9b, 0x3f, 0x4c, 0xf8, 0xaa, 0xb1, 0xdd, 0x66, 0x1e, 0x4d, 0xd0, 0xc5, 0x55, 0x8d, 0xc0, 0x59, 0x20, 0x2e, 0xe6, 0x46, 0x25, 0xa3, 0xb4, 0xb9, 0x2f, 0xf4, 0xd1, 0x56, 0x97, + 0xf1, 0x6c, 0x18, 0xd4, 0xd2, 0x33, 0x8c, 0xfb, 0x49, 0x6e, 0x07, 0x03, 0x52, 0x68, 0x71, 0xc9, 0x78, 0x4b, 0xac, 0x8e, 0xba, 0xe8, 0x27, 0x9c, 0xf2, 0x71, 0x3a, 0xf3, 0xcc, 0x2d, 0x44, 0x0e, + 0x8c, 0xd2, 0x00, 0x86, 0x7b, 0x85, 0x18, 0xaa, 0xd3, 0xb9, 0xe2, 0x85, 0x02, 0x7d, 0xa0, 0xad, 0xd9, 0xf0, 0x22, 0x9e, 0xd4, 0xe8, 0x42, 0xd0, 0x5e, 0x22, 0x6a, 0xda, 0xc1, 0x3a, 0x39, 0x52, + 0xe3, 0x83, 0x5c, 0x8f, 0xb0, 0xa4, 0x28, 0x74, 0xc9, 0x4c, 0x66, 0x1b, 0x39, 0xdf, 0x7b, 0x72, 0x88, 0x7d, 0x22, 0x7d, 0x58, 0x3c, 0xe6, 0xb3, 0xbd, 0x65, 0xf7, 0x95, 0x10, 0x7b, 0xd0, 0x93, + 0x38, 0x9b, 0xfe, 0xfd, 0x17, 0x68, 0xa5, 0x71, 0x6f, 0x68, 0x5b, 0x17, 0x4e, 0xd2, 0x3e, 0x94, 0xa5, 0x95, 0x6e, 0x29, 0xbb, 0x2d, 0xdb, 0x79, 0x21, 0x03, 0xe6, 0x2f, 0x68, 0x92, 0x8a, 0xcc, + 0x60, 0x3e, 0xec, 0x2f, 0xf5, 0x6d, 0xb1, 0x4c, 0x08, 0xb7, 0xcb, 0xe4, 0xe2, 0xb4, 0xf2, 0xe0, 0xea, 0xee, 0x54, 0x16, 0x2e, 0x95, 0xbb, 0x35, 0xef, 0x36, 0x30, 0x3e, 0xe3, 0xe6, 0xcc, 0x61, + 0x06, 0x13, 0x73, 0x87, 0x6f, 0x7a, 0x09, 0x6a, 0x8a, 0xf5, 0x7d, 0x78, 0x2f, 0x8c, 0x82, 0x03, 0xde, 0x93, 0x42, 0x3a, 0x37, 0x91, 0x22, 0xfe, 0x7d, 0xad, 0x77, 0x0c, 0x36, 0x90, 0xf9, 0x78, + 0x22, 0x84, 0x60, 0xd0, 0x25, 0xce, 0x93, 0xb1, 0xb3, 0x36, 0xc5, 0x73, 0xe4, 0xe5, 0x58, 0x40, 0xea, 0x65, 0xcf, 0xdd, 0x61, 0x22, 0xc6, 0x72, 0xc9, 0x12, 0xf5, 0x29, 0x39, 0xd9, 0xea, 0x5b, + 0xe0, 0x62, 0x10, 0xf5, 0xe7, 0xed, 0xb6, 0x5b, 0x66, 0x94, 0x5d, 0x70, 0x56, 0xf5, 0x59, 0xa7, 0xd6, 0x92, 0x53, 0xf4, 0xbd, 0xbc, 0x57, 0x9d, 0xe9, 0x64, 0xf3, 0xe9, 0x3a, 0x86, 0xfa, 0x38, + 0xb6, 0xa2, 0xc0, 0xb5, 0x43, 0x38, 0xdc, 0xe0, 0x93, 0xf0, 0xb4, 0x68, 0x4e, 0xe3, 0x61, 0x44, 0x9f, 0x16, 0xc2, 0x79, 0xa7, 0x2b, 0x77, 0x31, 0xe4, 0x46, 0x00, 0xa7, 0x02, 0x77, 0x68, 0xfd, + 0xd0, 0xf6, 0x43, 0xed, 0x10, 0x06, 0x4b, 0x98, 0xa9, 0xda, 0x03, 0x2f, 0x1f, 0x5d, 0xea, 0xd3, 0x11, 0xe1, 0x77, 0x33, 0x50, 0x94, 0xdb, 0x4e, 0x38, 0x51, 0x4e, 0xae, 0x15, 0xa8, 0xf8, 0xec, + 0xf2, 0xf2, 0x41, 0x4e, 0x37, 0x8e, 0xfb, 0xf9, 0x97, 0xb1, 0x06, 0x6b, 0x6f, 0x69, 0xd6, 0x69, 0x09, 0xa4, 0x7e, 0x29, 0x8a, 0x7f, 0xec, 0x96, 0x1a, 0x83, 0x78, 0x2e, 0x0e, 0x47, 0x0f, 0xe0, + 0x71, 0xde, 0xcf, 0x4b, 0x26, 0xac, 0xa6, 0xed, 0x68, 0x83, 0x59, 0xe1, 0x08, 0x50, 0x55, 0xfd, 0x2b, 0x5a, 0xe9, 0xf4, 0x91, 0x87, 0x49, 0x89, 0x7a, 0xf1, 0x33, 0x60, 0x60, 0x53, 0xd5, 0xf6, + 0xa8, 0x52, 0x8c, 0xcb, 0x31, 0xab, 0x7f, 0x3f, 0x2d, 0x89, 0xa9, 0x5c, 0x5f, 0x05, 0xb1, 0x57, 0x00, 0xe5, 0x32, 0xad, 0x81, 0xd5, 0x9d, 0x9d, 0xb8, 0xa2, 0xc2, 0x9c, 0xac, 0x93, 0x6e, 0x3f, + 0x33, 0xdf, 0xe2, 0x4b, 0x0b, 0x1b, 0x71, 0x90, 0x2d, 0xc9, 0xc3, 0x0e, 0xc8, 0xc7, 0x0b, 0xda, 0xba, 0x48, 0x4f, 0xcd, 0x2b, 0x94, 0x6d, 0x73, 0x5f, 0x16, 0xee, 0xad, 0x04, 0x03, 0x1c, 0xaf, + 0xde, 0x9e, 0xe0, 0x16, 0x96, 0xec, 0x9f, 0x0a, 0x8d, 0x5f, 0x36, 0xb6, 0x9c, 0x64, 0x2f, 0xfd, 0x0a, 0xd0, 0xd2, 0x54, 0x4f, 0x5e, 0x7f, 0xd8, 0x9a, 0x80, 0x49, 0x8e, 0xf6, 0x8e, 0x18, 0x16, + 0x17, 0xfa, 0xd4, 0x1e, 0x0b, 0xd5, 0x9b, 0xaa, 0xff, 0xee, 0xfe, 0x2f, 0x99, 0x72, 0x4c, 0x71, 0x9d, 0x47, 0xa2, 0xec, 0xba, 0x72, 0x1d, 0x76, 0xf2, 0x37, 0xeb, 0xa7, 0x3d, 0xb4, 0x7d, 0x88, + 0xb6, 0x99, 0xe3, 0x58, 0x2b, 0x07, 0x3c, 0x7e, 0xad, 0x2a, 0x5b, 0x3c, 0xf0, 0x24, 0x46, 0x63, 0x96, 0xf9, 0xf2, 0x82, 0x6c, 0xb7, 0x54, 0xf6, 0x60, 0x18, 0xe9, 0x50, 0x3f, 0x4a, 0xd1, 0xf9, + 0xd9, 0x21, 0x21, 0xaa, 0x99, 0x56, 0x50, 0x60, 0x51, 0xd5, 0x96, 0xff, 0xd4, 0x67, 0xe1, 0xaa, 0x8d, 0x96, 0x4c, 0x17, 0x67, 0xc9, 0x25, 0xb4, 0x68, 0xbb, 0xc9, 0x85, 0x06, 0x00, 0xc8, 0x43, + 0x49, 0x05, 0x41, 0xe8, 0x55, 0x5a, 0x3d, 0x8b, 0xd9, 0xf1, 0x87, 0x91, 0xef, 0x9e, 0xbd, 0x35, 0x94, 0xe7, 0x4c, 0x1f, 0xe3, 0xd3, 0xb8, 0x09, 0x40, 0xa8, 0xa0, 0x79, 0xf8, 0xd2, 0xca, 0x8d, + 0x30, 0x13, 0x4f, 0xc6, 0x6f, 0x87, 0x00, 0x81, 0x26, 0xe4, 0x3b, 0xd0, 0x6e, 0xb6, 0xe4, 0x1c, 0x3a, 0x70, 0xfa, 0x47, 0x39, 0x31, 0x9b, 0xf1, 0xa9, 0x32, 0xf0, 0x2c, 0x30, 0x64, 0x56, 0x56, + 0x0c, 0xda, 0x44, 0xdd, 0xac, 0x43, 0xed, 0x6d, 0x90, 0x04, 0x45, 0xf5, 0xbf, 0x85, 0xbb, 0x0c, 0xe3, 0x25, 0x94, 0x74, 0x36, 0xe0, 0xd0, 0x68, 0x5e, 0x41, 0xb1, 0x6b, 0xc7, 0x16, 0x95, 0x18, + 0x25, 0x9e, 0x57, 0x34, 0xfd, 0xce, 0x08, 0x0f, 0xfe, 0x85, 0x19, 0x1b, 0x1d, 0x8d, 0x8d, 0xe4, 0xdb, 0x48, 0x14, 0x3f, 0xb5, 0x64, 0x03, 0x8a, 0xce, 0x80, 0x10, 0x4d, 0x3a, 0x8d, 0x07, 0x12, + 0x45, 0xe2, 0xaa, 0x56, 0xc7, 0x19, 0x33, 0xf4, 0xdc, 0xf9, 0x25, 0xee, 0xe8, 0x44, 0xc8, 0x0f, 0xdd, 0xf3, 0x25, 0x1f, 0x74, 0x00, 0x6a, 0x23, 0x41, 0x33, 0x18, 0xbb, 0xfd, 0x2e, 0xd9, 0xe0, + 0x53, 0x51, 0xb5, 0xaa, 0xeb, 0xcc, 0x77, 0xcf, 0xac, 0x8d, 0x5f, 0x03, 0x64, 0x23, 0x1a, 0x50, 0xea, 0x86, 0x47, 0xc7, 0x2f, 0x71, 0x3e, 0x81, 0x7a, 0x20, 0x75, 0x32, 0x30, 0x29, 0xe3, 0xb8, + 0x8b, 0x72, 0x44, 0x22, 0x64, 0xc5, 0x97, 0xb0, 0xf1, 0xfc, 0x09, 0xf9, 0x40, 0x1c, 0xe8, 0x8a, 0xc9, 0x7c, 0x55, 0x22, 0xa5, 0x63, 0x64, 0x52, 0x3c, 0x37, 0xfe, 0xa2, 0xd6, 0xbd, 0x06, 0xb2, + }, + + }, +}; + +#define KYBER_TV_NUM sizeof(kyber_tv)/sizeof(struct KYBER_TEST_VECTOR) + diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/rsa_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/rsa_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/rsa_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/rsa_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -93,9 +93,9 @@ goto testcase_cleanup; } // begin testcase - testcase_begin("%s Encrypt and Decrypt with test vector %d." - "\npubl_exp='%s', modbits=%ld, publ_exp_len=%ld, " - "inputlen=%ld.", tsuite->name, i, s, + testcase_begin("%s Encrypt and Decrypt with test vector %u." + "\npubl_exp='%s', modbits=%lu, publ_exp_len=%lu, " + "inputlen=%lu.", tsuite->name, i, s, tsuite->tv[i].modbits, tsuite->tv[i].publ_exp_len, tsuite->tv[i].inputlen); @@ -103,7 +103,7 @@ if (!keysize_supported(slot_id, tsuite->mech.mechanism, tsuite->tv[i].modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", SLOT_ID, tsuite->tv[i].modbits); free(s); continue; @@ -270,8 +270,8 @@ if (decrypt_len != original_len) { testcase_fail("decrypted length does not match" - "original data length.\n expected length = %ld," - "but found length=%ld.\n", original_len, decrypt_len); + "original data length.\n expected length = %lu," + "but found length=%lu.\n", original_len, decrypt_len); } else if (memcmp(decrypt, original, original_len)) { testcase_fail("decrypted data does not match " "original data."); } else { @@ -343,7 +343,7 @@ CK_BYTE decrypt[BIG_REQUEST]; CK_ULONG decrypt_len; CK_MECHANISM mech; - CK_OBJECT_HANDLE publ_key, priv_key; + CK_OBJECT_HANDLE publ_key = CK_INVALID_HANDLE, priv_key = CK_INVALID_HANDLE; CK_SLOT_ID slot_id = SLOT_ID; CK_SESSION_HANDLE session; CK_FLAGS flags; @@ -378,8 +378,8 @@ goto testcase_cleanup; } // begin testcase - testcase_begin("%s Encrypt and Decrypt Import with test vector %d." - "\npubl_exp='%s', modbits=%ld, publ_exp_len=%ld.", + testcase_begin("%s Encrypt and Decrypt Import with test vector %u." + "\npubl_exp='%s', modbits=%lu, publ_exp_len=%lu.", tsuite->name, i, s, tsuite->tv[i].mod_len * 8, tsuite->tv[i].pubexp_len); @@ -388,23 +388,23 @@ if (!keysize_supported(slot_id, tsuite->mech.mechanism, tsuite->tv[i].mod_len * 8)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", SLOT_ID, tsuite->tv[i].mod_len * 8); free(s); continue; } - if (is_ep11_token(slot_id)) { + if (is_ep11_token(slot_id) || is_icsf_token(slot_id)) { if (!is_valid_ep11_pubexp(tsuite->tv[i].pub_exp, tsuite->tv[i].pubexp_len)) { - testcase_skip("EP11 Token cannot be used with publ_exp.='%s'", s); + testcase_skip("EP11/ICSF Token cannot be used with publ_exp.='%s'", s); free(s); continue; } // modulus length must be multiple of 128 byte // skip test if modulus length has unsuported size if ((tsuite->tv[i].mod_len % 128) != 0) { - testcase_skip("EP11 Token cannot be used with this test vector."); + testcase_skip("EP11/ICSF Token cannot be used with this test vector."); free(s); continue; } @@ -592,8 +592,8 @@ if (decrypt_len != original_len) { testcase_fail("decrypted length does not match" - "original data length.\n expected length = %ld," - "but found length=%ld.\n", original_len, decrypt_len); + "original data length.\n expected length = %lu," + "but found length=%lu.\n", original_len, decrypt_len); } else if (memcmp(decrypt, original, original_len)) { testcase_fail("decrypted data does not match " "original data."); } else { @@ -710,7 +710,7 @@ goto testcase_cleanup; } // begin test - testcase_begin("%s Sign%s and Verify%s with test vector %d, " + testcase_begin("%s Sign%s and Verify%s with test vector %u, " "\npubl_exp='%s', mod_bits='%lu', keylen='%lu'.", tsuite->name, recover_mode ? "Recover" : "", recover_mode ? "Recover" : "", i, s, @@ -718,7 +718,7 @@ if (!keysize_supported(slot_id, tsuite->mech.mechanism, tsuite->tv[i].modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", SLOT_ID, tsuite->tv[i].modbits); free(s); continue; @@ -828,7 +828,7 @@ rc = funcs->C_Sign(session, message, message_len, signature, &signature_len); if (rc != CKR_OK) { - testcase_error("C_Sign%s(), rc=%s signature len=%ld", + testcase_error("C_Sign%s(), rc=%s signature len=%lu", recover_mode ? "Recover" : "", p11_get_ckr(rc), signature_len); goto error; @@ -974,14 +974,14 @@ goto testcase_cleanup; } // begin test - testcase_begin("%s Sign and Verify with test vector %d, " + testcase_begin("%s Sign and Verify with test vector %u, " "\npubl_exp='%s', mod_bits='%lu', keylen='%lu'.", tsuite->name, i, s, tsuite->tv[i].modbits, tsuite->tv[i].keylen); if (!keysize_supported(slot_id, tsuite->mech.mechanism, tsuite->tv[i].modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", SLOT_ID, tsuite->tv[i].modbits); free(s); continue; @@ -1083,7 +1083,7 @@ rc = funcs->C_Sign(session, message, message_len, signature, &signature_len); if (rc != CKR_OK) { - testcase_error("C_Sign(), rc=%s signature len=%ld", + testcase_error("C_Sign(), rc=%s signature len=%lu", p11_get_ckr(rc), signature_len); goto error; } @@ -1212,7 +1212,7 @@ if (!keysize_supported(slot_id, tsuite->mech.mechanism, tsuite->tv[i].modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", SLOT_ID, tsuite->tv[i].modbits); continue; } @@ -1292,7 +1292,7 @@ } // begin test - testcase_begin("%s Wrap Unwrap with test vector %d, " + testcase_begin("%s Wrap Unwrap with test vector %u, " "\npubl_exp='%s', mod_bits='%lu', keylen='%lu', " "keytype='%s'", tsuite->name, i, s, tsuite->tv[i].modbits, tsuite->tv[i].keylen, @@ -1313,6 +1313,12 @@ (unsigned int)keygen_mech.mechanism); continue; } + if (keygen_mech.mechanism == CKM_AES_XTS_KEY_GEN && + is_ep11_token(slot_id)) { + testcase_skip("Skip test as CKM_AES_XTS_KEY_GEN is supported " \ + "only for protected keys in EP11 token"); + continue; + } // get wrapping mechanism wrap_mech = tsuite->mech; if (wrap_mech.mechanism == CKM_RSA_PKCS_OAEP) { @@ -1388,6 +1394,12 @@ mech.pParameter = &aes_iv; key_type = CKK_AES; break; + case CKM_AES_XTS_KEY_GEN: + mech.mechanism = CKM_AES_XTS; + mech.ulParameterLen = AES_IV_SIZE; + mech.pParameter = &aes_iv; + key_type = CKK_AES_XTS; + break; case CKM_DES3_KEY_GEN: mech.mechanism = CKM_DES3_CBC; mech.ulParameterLen = DES_IV_SIZE; @@ -1400,12 +1412,6 @@ mech.pParameter = &des_iv; key_type = CKK_DES; break; - case CKM_CDMF_KEY_GEN: - mech.mechanism = CKM_CDMF_CBC; - mech.ulParameterLen = DES_IV_SIZE; - mech.pParameter = &des_iv; - key_type = CKK_CDMF; - break; default: testcase_error("unknown mech"); goto error; @@ -1480,6 +1486,7 @@ * unwrapping the key. */ if (((keygen_mech.mechanism == CKM_AES_KEY_GEN) || + (keygen_mech.mechanism == CKM_AES_XTS_KEY_GEN) || (keygen_mech.mechanism == CKM_GENERIC_SECRET_KEY_GEN)) && (wrap_mech.mechanism == CKM_RSA_X_509)) { unwrapped_keylen = tsuite->tv[i].keylen; @@ -1625,10 +1632,17 @@ } // iterate over test vectors for (i = 0; i < tsuite->tvcount; i++) { - testcase_begin("%s Sign with test vector %d.", tsuite->name, i); + testcase_begin("%s Sign with test vector %u.", tsuite->name, i); rc = CKR_OK; // set return value + if (!keysize_supported(slot_id, tsuite->mech.mechanism, + tsuite->tv[i].mod_len * 8)) { + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", + SLOT_ID, tsuite->tv[i].mod_len * 8); + continue; + } + // special case for ica // prime1, prime2, exp1, exp2, coef // must be size mod_len/2 or smaller @@ -1648,14 +1662,14 @@ testcase_skip("ICA Token cannot be used with this test vector."); continue; } - } - // special case for EP11 + + // special case for EP11 + ICSF // modulus length must be multiple of 128 byte // skip test if modulus length has unsuported size - if (is_ep11_token(slot_id)) { + if (is_ep11_token(slot_id) || is_icsf_token(slot_id)) { if ((tsuite->tv[i].mod_len % 128) != 0) { - testcase_skip("EP11 Token cannot be used with this test vector."); + testcase_skip("EP11/ICSF Token cannot be used with this test vector."); continue; } } @@ -1747,11 +1761,11 @@ testcase_new_assertion(); if (actual_len != expected_len) { - testcase_fail("%s Sign with test vector %d failed. " - "Expected len=%ld, found len=%ld.", + testcase_fail("%s Sign with test vector %u failed. " + "Expected len=%lu, found len=%lu.", tsuite->name, i, expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { - testcase_fail("%s Sign with test vector %d failed. " + testcase_fail("%s Sign with test vector %u failed. " "Signature data does not match test vector " "signature.", tsuite->name, i); @@ -1826,16 +1840,23 @@ // iterate over test vectors for (i = 0; i < tsuite->tvcount; i++) { - testcase_begin("%s Verify with test vector %d.", tsuite->name, i); + testcase_begin("%s Verify with test vector %u.", tsuite->name, i); rc = CKR_OK; // set return value - // special case for EP11 + if (!keysize_supported(slot_id, tsuite->mech.mechanism, + tsuite->tv[i].mod_len * 8)) { + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", + SLOT_ID, tsuite->tv[i].mod_len * 8); + continue; + } + + // special case for EP11 + ICSF // modulus length must be multiple of 128 byte // skip test if modulus length has unsuported size - if (is_ep11_token(slot_id)) { + if (is_ep11_token(slot_id) || is_icsf_token(slot_id)) { if ((tsuite->tv[i].mod_len % 128) != 0) { - testcase_skip("EP11 Token cannot be used with this test vector."); + testcase_skip("EP11/ICSF Token cannot be used with this test vector."); continue; } } @@ -1913,7 +1934,7 @@ if (rc == CKR_OK) { testcase_pass("C_Verify."); } else { - testcase_fail("%s Sign Verify with test vector %d " + testcase_fail("%s Sign Verify with test vector %u " "failed.", tsuite->name, i); } @@ -1942,7 +1963,7 @@ return rc; } -CK_RV rsa_funcs() +CK_RV rsa_funcs(void) { unsigned int i; CK_RV rv = CKR_OK; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/rsa.h opencryptoki-3.20.0+dfsg/testcases/crypto/rsa.h --- opencryptoki-3.18.0+dfsg/testcases/crypto/rsa.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/rsa.h 2023-02-13 09:22:42.000000000 +0100 @@ -177,17 +177,7 @@ .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0} }, - { // #13 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = {0x01, 0x00, 0x01}, - .inputlen = 16, - .oaep_params = {CKM_SHA512, CKG_MGF1_SHA512, CKZ_DATA_SPECIFIED, - "abcdefghijkl", 12}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // #14 + { // #13 .modbits = 4096, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, @@ -203,7 +193,7 @@ struct GENERATED_TEST_SUITE_INFO generated_oaep_test_suites[] = { { .name = "RSA PKCS OAEP", - .tvcount = 15, + .tvcount = 14, .tv = rsa_oaep_generated_tv, .mech = {CKM_RSA_PKCS_OAEP, 0, 0}, } @@ -556,687 +546,625 @@ .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 2 - .modbits = 512, - .publ_exp_len = 1, - .publ_exp = {0x03}, - .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 3 + { // 2 .modbits = 512, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 4 + { // 3 .modbits = 512, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 5 + { // 4 .modbits = 512, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 6 + { // 5 .modbits = 512, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 32, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 7 - .modbits = 512, - .publ_exp_len = 2, - .publ_exp = {0x00, 0x11}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 8 + { // 6 .modbits = 512, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 9 + { // 7 .modbits = 512, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 10 + { // 8 .modbits = 512, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 11 + { // 9 .modbits = 512, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 12 + { // 10 .modbits = 512, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 13 - .modbits = 512, - .publ_exp_len = 3, - .publ_exp = {0x01, 0x00, 0x01}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 14 + { // 11 .modbits = 512, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 15 + { // 12 .modbits = 512, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 16 + { // 13 .modbits = 512, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 17 + { // 14 .modbits = 512, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 18 + { // 15 .modbits = 768, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0} }, - { // 19 - .modbits = 768, - .publ_exp_len = 1, - .publ_exp = {0x03}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 20 + { // 16 .modbits = 768, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 21 + { // 17 .modbits = 768, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 22 + { // 18 .modbits = 768, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 23 + { // 19 .modbits = 768, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 24 + { // 20 .modbits = 768, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 64, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 25 + { // 21 .modbits = 768, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 26 - .modbits = 768, - .publ_exp_len = 2, - .publ_exp = {0x00, 0x11}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 27 + { // 22 .modbits = 768, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 28 + { // 23 .modbits = 768, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0} }, - { // 29 + { // 24 .modbits = 768, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 30 + { // 25 .modbits = 768, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 31 + { // 26 .modbits = 768, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 64, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 32 + { // 27 .modbits = 768, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 33 - .modbits = 768, - .publ_exp_len = 3, - .publ_exp = {0x01, 0x00, 0x01}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 34 + { // 28 .modbits = 768, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 35 + { // 29 .modbits = 768, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 36 + { // 30 .modbits = 768, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 37 + { // 31 .modbits = 768, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 38 + { // 32 .modbits = 1024, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 39 - .modbits = 1024, - .publ_exp_len = 1, - .publ_exp = {0x03}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 40 + { // 33 .modbits = 1024, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 41 + { // 34 .modbits = 1024, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 42 + { // 35 .modbits = 1024, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 43 + { // 36 .modbits = 1024, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 44 + { // 37 .modbits = 1024, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 96, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 45 + { // 38 .modbits = 1024, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 46 - .modbits = 1024, - .publ_exp_len = 2, - .publ_exp = {0x00, 0x11}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 47 + { // 39 .modbits = 1024, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 48 + { // 40 .modbits = 1024, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 49 + { // 41 .modbits = 1024, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 50 + { // 42 .modbits = 1024, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 51 + { // 43 .modbits = 1024, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 64, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 52 + { // 44 .modbits = 1024, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 53 - .modbits = 1024, - .publ_exp_len = 3, - .publ_exp = {0x01, 0x00, 0x01}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 54 + { // 45 .modbits = 1024, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 55 + { // 46 .modbits = 1024, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 56 + { // 47 .modbits = 1024, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 57 + { // 48 .modbits = 1024, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 58 + { // 49 .modbits = 1024, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 32, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 59 + { // 50 .modbits = 2048, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 60 - .modbits = 2048, - .publ_exp_len = 1, - .publ_exp = {0x03}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 61 + { // 51 .modbits = 2048, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 62 + { // 52 .modbits = 2048, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 63 + { // 53 .modbits = 2048, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 64 + { // 54 .modbits = 2048, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 65 + { // 55 .modbits = 2048, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 64, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 66 + { // 56 .modbits = 2048, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 67 - .modbits = 2048, - .publ_exp_len = 2, - .publ_exp = {0x00, 0x11}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 68 + { // 57 .modbits = 2048, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 69 + { // 58 .modbits = 2048, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 70 + { // 59 .modbits = 2048, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 71 + { // 60 .modbits = 2048, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 72 + { // 61 .modbits = 2048, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 128, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 73 + { // 62 .modbits = 2048, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 74 - .modbits = 2048, - .publ_exp_len = 3, - .publ_exp = {0x01, 0x00, 0x01}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 75 + { // 63 .modbits = 2048, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 76 + { // 64 .modbits = 2048, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 77 + { // 65 .modbits = 2048, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 78 + { // 66 .modbits = 2048, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 79 + { // 67 .modbits = 4096, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 80 - .modbits = 4096, - .publ_exp_len = 1, - .publ_exp = {0x03}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 81 + { // 68 .modbits = 4096, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 82 + { // 69 .modbits = 4096, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 83 + { // 70 .modbits = 4096, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 84 + { // 71 .modbits = 4096, .publ_exp_len = 1, .publ_exp = {0x03}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 85 + { // 72 .modbits = 4096, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 86 - .modbits = 4096, - .publ_exp_len = 2, - .publ_exp = {0x00, 0x11}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 87 + { // 73 .modbits = 4096, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 88 + { // 74 .modbits = 4096, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 89 + { // 75 .modbits = 4096, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 90 + { // 76 .modbits = 4096, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 91 + { // 77 .modbits = 4096, .publ_exp_len = 2, .publ_exp = {0x00, 0x11}, .keylen = 256, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 92 + { // 78 .modbits = 4096, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 10, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, }, - { // 93 - .modbits = 4096, - .publ_exp_len = 3, - .publ_exp = {0x01, 0x00, 0x01}, - .keylen = 8, - .keytype = {CKM_CDMF_KEY_GEN, 0, 0}, - }, - { // 94 + + { // 79 .modbits = 4096, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 8, .keytype = {CKM_DES_KEY_GEN, 0, 0}, }, - { // 95 + { // 80 .modbits = 4096, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 24, .keytype = {CKM_DES3_KEY_GEN, 0, 0}, }, - { // 96 + { // 81 .modbits = 4096, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 16, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 97 + { // 82 .modbits = 4096, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 32, .keytype = {CKM_AES_KEY_GEN, 0, 0}, }, - { // 98 + { // 83 .modbits = 4096, .publ_exp_len = 3, .publ_exp = {0x01, 0x00, 0x01}, .keylen = 256, .keytype = {CKM_GENERIC_SECRET_KEY_GEN, 0, 0}, - } + }, + { // 84 + .modbits = 1024, + .publ_exp_len = 3, + .publ_exp = {0x01, 0x00, 0x01}, + .keylen = 32, + .keytype = {CKM_AES_XTS_KEY_GEN, 0, 0}, + }, + { // 85 + .modbits = 1024, + .publ_exp_len = 3, + .publ_exp = {0x01, 0x00, 0x01}, + .keylen = 64, + .keytype = {CKM_AES_XTS_KEY_GEN, 0, 0}, + }, + { // 86 + .modbits = 2048, + .publ_exp_len = 3, + .publ_exp = {0x01, 0x00, 0x01}, + .keylen = 32, + .keytype = {CKM_AES_XTS_KEY_GEN, 0, 0}, + }, + { // 87 + .modbits = 2048, + .publ_exp_len = 3, + .publ_exp = {0x01, 0x00, 0x01}, + .keylen = 64, + .keytype = {CKM_AES_XTS_KEY_GEN, 0, 0}, + }, + { // 88 + .modbits = 4096, + .publ_exp_len = 3, + .publ_exp = {0x01, 0x00, 0x01}, + .keylen = 32, + .keytype = {CKM_AES_XTS_KEY_GEN, 0, 0}, + }, + { // 89 + .modbits = 4096, + .publ_exp_len = 3, + .publ_exp = {0x01, 0x00, 0x01}, + .keylen = 64, + .keytype = {CKM_AES_XTS_KEY_GEN, 0, 0}, + }, }; static struct RSA_GENERATED_TEST_VECTOR rsa_generated_tv[] = { @@ -1692,13 +1620,13 @@ struct GENERATED_TEST_SUITE_INFO generated_keywrap_test_suites[] = { { .name = "RSA PKCS", - .tvcount = 99, + .tvcount = 90, .tv = rsa_keywrap_generated_tv, .mech = {CKM_RSA_PKCS, 0, 0}, }, { .name = "RSA X.509", - .tvcount = 99, + .tvcount = 90, .tv = rsa_keywrap_generated_tv, .mech = {CKM_RSA_X_509, 0, 0}, } diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/rsaupdate_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/rsaupdate_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/rsaupdate_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/rsaupdate_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -89,14 +89,14 @@ } // begin test - testcase_begin("%s Sign and Verify with test vector %d, " + testcase_begin("%s Sign and Verify with test vector %u, " "\npubl_exp='%s', mod_bits='%lu', keylen='%lu'.", tsuite->name, i, s, tsuite->tv[i].modbits, tsuite->tv[i].keylen); if (!keysize_supported(slot_id, tsuite->mech.mechanism, tsuite->tv[i].modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", SLOT_ID, tsuite->tv[i].modbits); free(s); continue; @@ -229,7 +229,7 @@ testcase_pass("C_SignFinal set output length."); } else { testcase_fail("C_SignFinal failed to set length: " - "expected %ld, got %ld.", + "expected %lu, got %lu.", signature_len, tsuite->tv[i].modbits / 8); goto error; } @@ -370,14 +370,14 @@ goto testcase_cleanup; } // begin test - testcase_begin("%s Sign and Verify with test vector %d, " + testcase_begin("%s Sign and Verify with test vector %u, " "\npubl_exp='%s', mod_bits='%lu', keylen='%lu'.", tsuite->name, i, s, tsuite->tv[i].modbits, tsuite->tv[i].keylen); if (!keysize_supported(slot_id, tsuite->mech.mechanism, tsuite->tv[i].modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", SLOT_ID, tsuite->tv[i].modbits); free(s); continue; @@ -501,7 +501,7 @@ testcase_pass("C_SignFinal set output length."); } else { testcase_fail("C_SignFinal failed to set length: " - "expected %ld, got %ld.", + "expected %lu, got %lu.", signature_len, tsuite->tv[i].modbits / 8); goto error; } @@ -643,7 +643,15 @@ goto testcase_cleanup; } - testcase_begin("%s Verify with test vector %d.", tsuite->name, i); + testcase_begin("%s Verify with test vector %u.", tsuite->name, i); + + if (!keysize_supported(slot_id, tsuite->mech.mechanism, + tsuite->tv[i].mod_len * 8)) { + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", + SLOT_ID, tsuite->tv[i].mod_len * 8); + free(s); + continue; + } // special case for EP11 // modulus length must be multiple of 128 byte @@ -760,7 +768,7 @@ if (rc == CKR_OK) { testcase_pass("C_Verify."); } else { - testcase_fail("%s Sign Verify with test vector %d " + testcase_fail("%s Sign Verify with test vector %u " "failed.", tsuite->name, i); } @@ -840,7 +848,15 @@ rc = -1; goto testcase_cleanup; } - testcase_begin("%s Sign with test vector %d.", tsuite->name, i); + testcase_begin("%s Sign with test vector %u.", tsuite->name, i); + + if (!keysize_supported(slot_id, tsuite->mech.mechanism, + tsuite->tv[i].mod_len * 8)) { + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", + SLOT_ID, tsuite->tv[i].mod_len * 8); + free(s); + continue; + } // special case for ica // prime1, prime2, exp1, exp2, coef @@ -1013,7 +1029,7 @@ testcase_pass("C_SignFinal set output length."); } else { testcase_fail("C_SignFinal failed to set length: " - "expected %ld, got %ld.", + "expected %lu, got %lu.", actual_len, tsuite->tv[i].mod_len); goto error; } @@ -1027,11 +1043,11 @@ testcase_new_assertion(); if (actual_len != expected_len) { - testcase_fail("%s Sign with test vector %d failed. " - "Expected len=%ld, found len=%ld.", + testcase_fail("%s Sign with test vector %u failed. " + "Expected len=%lu, found len=%lu.", tsuite->name, i, expected_len, actual_len); } else if (memcmp(actual, expected, expected_len)) { - testcase_fail("%s Sign with test vector %d failed. " + testcase_fail("%s Sign with test vector %u failed. " "Signature data does not match test vector " "signature.", tsuite->name, i); @@ -1062,7 +1078,7 @@ return rc; } -CK_RV rsa_funcs() +CK_RV rsa_funcs(void) { unsigned int i; CK_RV rv = CKR_OK; diff -Nru opencryptoki-3.18.0+dfsg/testcases/crypto/ssl3_func.c opencryptoki-3.20.0+dfsg/testcases/crypto/ssl3_func.c --- opencryptoki-3.18.0+dfsg/testcases/crypto/ssl3_func.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/crypto/ssl3_func.c 2023-02-13 09:22:42.000000000 +0100 @@ -147,7 +147,7 @@ for (i = 0; i < 500; i += 100) { rc = funcs->C_SignUpdate(session, &data2[i], 100); if (rc != CKR_OK) { - testcase_error("Iteration #%ld, C_SignUpdate() rc = %s", i / 100, + testcase_error("Iteration #%lu, C_SignUpdate() rc = %s", i / 100, p11_get_ckr(rc)); goto done; } @@ -177,7 +177,7 @@ for (i = 0; i < 500; i += 100) { rc = funcs->C_VerifyUpdate(session, &data2[i], 100); if (rc != CKR_OK) { - testcase_error("Iteration #%ld, C_VerifyUpdate() rc = %s", i / 100, + testcase_error("Iteration #%lu, C_VerifyUpdate() rc = %s", i / 100, p11_get_ckr(rc)); goto done; } @@ -637,7 +637,210 @@ return rc; } -CK_RV ssl3_functions() +CK_RV do_TLS_PreMasterKeyGen(CK_SESSION_HANDLE session) +{ + CK_MECHANISM mech; + CK_VERSION version; + CK_OBJECT_HANDLE h_key; + CK_RV rc = CKR_OK; + CK_SLOT_ID slot_id = SLOT_ID; + + testcase_begin("starting do_TLS_PreMasterKeyGen...\n"); + + version.major = 3; + version.minor = 3; + + mech.mechanism = CKM_TLS_PRE_MASTER_KEY_GEN; + mech.pParameter = &version; + mech.ulParameterLen = sizeof(CK_VERSION); + + /** skip test if the slot doesn't support this mechanism **/ + if (!mech_supported(slot_id, mech.mechanism)) { + testsuite_skip(1, "Slot %u doesn't support %s (0x%x)", + (unsigned int) slot_id, + mech_to_str(mech.mechanism), + (unsigned int) mech.mechanism); + goto done; + } + + testcase_new_assertion(); + rc = funcs->C_GenerateKey(session, &mech, NULL, 0, &h_key); + if (rc != CKR_OK) { + if (is_rejected_by_policy(rc, session)) { + testcase_skip("key generation is not allowed by policy"); + return CKR_OK; + } + testcase_fail("C_GenerateKey() rc = %s", p11_get_ckr(rc)); + } else { + testcase_pass("Successfully generated a generic secret key."); + } + + if (funcs->C_DestroyObject(session, h_key) != CKR_OK) + testcase_error("C_DestroyObject() failed"); + +done: + return rc; +} + +CK_RV do_TLS_MultipleKeysDerive(CK_SESSION_HANDLE session) +{ + CK_MECHANISM mech; + CK_OBJECT_HANDLE h_pm_secret; + CK_RV rc = CKR_OK; + CK_ULONG i; + + CK_VERSION version = { 3, 3 }; + CK_BBOOL true_value = TRUE; + CK_BBOOL false_value = FALSE; + CK_ATTRIBUTE pm_tmpl[] = { + {CKA_TOKEN, &true_value, sizeof(true_value)}, + }; + + CK_BYTE client_random_data[32]; + CK_BYTE server_random_data[32]; + CK_ATTRIBUTE incomplete_tmpl[] = { + {CKA_TOKEN, &false_value, sizeof(false_value)}, + {CKA_SENSITIVE, &false_value, sizeof(false_value)}, + {CKA_EXTRACTABLE, &true_value, sizeof(true_value)} + }; + + CK_OBJECT_CLASS class = CKO_SECRET_KEY; + CK_KEY_TYPE key_type = CKK_AES; + CK_ULONG key_len = 16; + CK_ATTRIBUTE complete_tmpl[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &key_type, sizeof(key_type)}, + {CKA_VALUE_LEN, &key_len, sizeof(CK_ULONG)}, + {CKA_TOKEN, &false_value, sizeof(false_value)}, + {CKA_SENSITIVE, &false_value, sizeof(false_value)}, + {CKA_EXTRACTABLE, &true_value, sizeof(true_value)} + }; + + CK_BYTE iv_client[128 / 8] = { 0, }; + CK_BYTE iv_server[128 / 8] = { 0, }; + + CK_SSL3_KEY_MAT_OUT param_out = { + .hClientMacSecret = 0, + .hServerMacSecret = 0, + .hClientKey = 0, + .hServerKey = 0, + .pIVClient = iv_client, + .pIVServer = iv_server, + }; + + CK_SSL3_KEY_MAT_PARAMS params = { + .ulMacSizeInBits = 128, + .ulKeySizeInBits = key_len * 8, + .ulIVSizeInBits = 128, + .bIsExport = FALSE, + .RandomInfo = + { + .pClientRandom = client_random_data, + .ulClientRandomLen = sizeof(client_random_data), + .pServerRandom = server_random_data, + .ulServerRandomLen = sizeof(server_random_data), + }, + .pReturnedKeyMaterial = ¶m_out, + }; + CK_SLOT_ID slot_id = SLOT_ID; + + testcase_begin("starting do_TLS_MultipleKeysDerive...\n"); + + // generate the pre-master secret key + // + mech.mechanism = CKM_TLS_PRE_MASTER_KEY_GEN; + mech.pParameter = &version; + mech.ulParameterLen = sizeof(CK_VERSION); + + /** skip test if the slot doesn't support this mechanism **/ + if (!mech_supported(slot_id, mech.mechanism)) { + testsuite_skip(3, "Slot %u doesn't support %s (0x%x)", + (unsigned int) slot_id, + mech_to_str(mech.mechanism), + (unsigned int) mech.mechanism); + goto skipped; + } + + testcase_new_assertion(); + rc = funcs->C_GenerateKey(session, &mech, pm_tmpl, + sizeof(pm_tmpl) / sizeof(*pm_tmpl), &h_pm_secret); + if (rc != CKR_OK) { + if (is_rejected_by_policy(rc, session)) { + testcase_skip("Key generation is not allowed by policy"); + goto done; + } + testcase_fail("C_GenerateKey() rc= %s", p11_get_ckr(rc)); + goto done; + } else { + testcase_pass("Successfully generated a generic secret key."); + } + + for (i = 0; i < sizeof(client_random_data); i++) { + client_random_data[i] = i; + server_random_data[i] = sizeof(client_random_data) - i; + } + + mech.mechanism = CKM_TLS_KEY_AND_MAC_DERIVE; + mech.pParameter = ¶ms; + mech.ulParameterLen = sizeof(params); + + /* + * Try deriving the key without required attributes... + */ + testcase_new_assertion(); + rc = funcs->C_DeriveKey(session, &mech, h_pm_secret, incomplete_tmpl, + sizeof(incomplete_tmpl) / sizeof(*incomplete_tmpl), + NULL); + if (is_rejected_by_policy(rc, session)) { + testcase_skip("key derivation is not allowed by policy"); + goto done; + } + if (rc != CKR_TEMPLATE_INCOMPLETE) { + testcase_fail("C_DeriveKey did not recognize missing attributes."); + goto done; + } else { + testcase_pass("Success, could not derive key without required " + "attributes."); + } + + /* + * Now derive key with required attributes... + */ + + testcase_new_assertion(); + rc = funcs->C_DeriveKey(session, &mech, h_pm_secret, complete_tmpl, + sizeof(complete_tmpl) / sizeof(*complete_tmpl), + NULL); + if (rc != CKR_OK) { + if (is_rejected_by_policy(rc, session)) { + testcase_skip("key derivation is not allowed by policy"); + goto done; + } + testcase_fail("C_DeriveKey() rc= %s", p11_get_ckr(rc)); + goto done; + } else { + testcase_pass("Successfully derived a keys from pre-master."); + } + + + if (funcs->C_DestroyObject(session, param_out.hClientMacSecret)) + testcase_error("C_DestroyObject rc=%s", p11_get_ckr(rc)); + if (funcs->C_DestroyObject(session, param_out.hServerMacSecret)) + testcase_error("C_DestroyObject rc=%s", p11_get_ckr(rc)); + if (funcs->C_DestroyObject(session, param_out.hClientKey)) + testcase_error("C_DestroyObject rc=%s", p11_get_ckr(rc)); + if (funcs->C_DestroyObject(session, param_out.hServerKey)) + testcase_error("C_DestroyObject rc=%s", p11_get_ckr(rc)); + +done: + if (funcs->C_DestroyObject(session, h_pm_secret) != CKR_OK) + testcase_error("C_DestroyObject() failed"); + +skipped: + return rc; +} + +CK_RV ssl3_functions(void) { CK_RV rc; SYSTEMTIME t1, t2; @@ -685,6 +888,20 @@ GetSystemTime(&t2); process_time(t1, t2); + GetSystemTime(&t1); + rc = do_TLS_PreMasterKeyGen(session); + if (rc && !no_stop) + goto testcase_cleanup; + GetSystemTime(&t2); + process_time(t1, t2); + + GetSystemTime(&t1); + rc = do_TLS_MultipleKeysDerive(session); + if (rc && !no_stop) + goto testcase_cleanup; + GetSystemTime(&t2); + process_time(t1, t2); + testcase_cleanup: testcase_user_logout(); rc = funcs->C_CloseAllSessions(slot_id); diff -Nru opencryptoki-3.18.0+dfsg/testcases/init_vhsm.exp.in opencryptoki-3.20.0+dfsg/testcases/init_vhsm.exp.in --- opencryptoki-3.18.0+dfsg/testcases/init_vhsm.exp.in 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/init_vhsm.exp.in 2023-02-13 09:22:42.000000000 +0100 @@ -20,6 +20,11 @@ timeout { send_user "Timeout on VHSM pin\n"; exit 1 } } expect { + "Re-enter the new VHSM PIN:" { sleep .1; send $env(PKCS11_VHSM_PIN); send "\r"; } + eof { send_user "Unexpected EOF on VHSM pin\n"; exit 1 } + timeout { send_user "Timeout on VHSM pin\n"; exit 1 } +} +expect { "VHSM-pin successfully set." {} eof { send_user "Unexpected EOF at the end\n"; exit 1 } timeout { send_user "Unexpected timeout at the end\n"; exit 1 } diff -Nru opencryptoki-3.18.0+dfsg/testcases/login/login_flags.c opencryptoki-3.20.0+dfsg/testcases/login/login_flags.c --- opencryptoki-3.18.0+dfsg/testcases/login/login_flags.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/login/login_flags.c 2023-02-13 09:22:42.000000000 +0100 @@ -65,7 +65,7 @@ } } - printf("Using slot %ld...\n\n", slot_id); + printf("Using slot %lu...\n\n", slot_id); if (do_GetFunctionList()) return -1; @@ -124,7 +124,7 @@ * It should now be the slot number of the token we're using */ if (si.slotID != slot_id) { - printf("Test #2 failed. Slot ID was %ld, expected %ld\n", si.slotID, + printf("Test #2 failed. Slot ID was %lu, expected %lu\n", si.slotID, slot_id); goto session_close; } @@ -135,13 +135,13 @@ } if (ti.flags & CKF_USER_PIN_LOCKED) { - printf("The USER's PIN is locked for the token in slot %ld.\n" + printf("The USER's PIN is locked for the token in slot %lu.\n" "Please reset the USER's PIN and re-run this test.\n", slot_id); goto session_close; } if (!(ti.flags & CKF_TOKEN_INITIALIZED)) { - printf("The token in slot %ld is uninitialized.\n", slot_id); + printf("The token in slot %lu is uninitialized.\n", slot_id); goto session_close; } // 3. Login/Logout with correct USER PIN @@ -281,7 +281,7 @@ goto session_close; } - printf("Tests succeeded. USER PIN is now locked for slot %ld.\n" + printf("Tests succeeded. USER PIN is now locked for slot %lu.\n" "Re-running this test should return CKR_PIN_LOCKED.\n" "To unlock this slot, run the init_tok testcase on the slot.\n", slot_id); diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/cca_export_import_test.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/cca_export_import_test.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/cca_export_import_test.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/cca_export_import_test.c 2023-02-13 09:22:42.000000000 +0100 @@ -605,11 +605,11 @@ for (keylen = 16; keylen <= 32; keylen += 8) { - testcase_begin("CCA export/import test with AES%d data key", 8 * keylen); + testcase_begin("CCA export/import test with AES%u data key", 8 * keylen); // create ock aes key - rc = create_AESKey(session, CK_TRUE, key, keylen, &hkey); + rc = create_AESKey(session, CK_TRUE, key, keylen, CKK_AES, &hkey); if (rc != CKR_OK) { if (rc == CKR_POLICY_VIOLATION) { testcase_skip("AES key generation is not allowed by policy"); @@ -682,7 +682,7 @@ goto error; } - testcase_pass("CCA export/import test with AES%d data key: ok", 8 * keylen); + testcase_pass("CCA export/import test with AES%u data key: ok", 8 * keylen); error: free(opaquekey); @@ -724,7 +724,7 @@ for (i = 0; keybitlen[i]; i++) { - testcase_begin("CCA import test with AES%d cipher key", keybitlen[i]); + testcase_begin("CCA import test with AES%u cipher key", keybitlen[i]); // Opencryptoki can't create CCA AES cipher keys. // So let's read a raw CCA AES cipher key from the pkey sysfs api @@ -774,7 +774,7 @@ // that's it here - testcase_pass("CCA import test with AES%d cipher key: ok", keybitlen[i]); + testcase_pass("CCA import test with AES%u cipher key: ok", keybitlen[i]); error: ; diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/dual_functions.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/dual_functions.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/dual_functions.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/dual_functions.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,1055 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +/* File: dual_functions.c + * + * Test driver. In-depth regression test for PKCS #11 + */ + +#include +#include +#include +#include +#include + +#include "pkcs11types.h" +#include "regress.h" +#include "common.c" +#include "mechtable.h" +#include "mech_to_str.h" + +CK_BYTE aes_iv[16] = { 0x00,0x01,0x02,0x03,0x04,0x05,0x06,0x07, + 0x08,0x09,0x0a,0x0b,0x0c,0x0d,0x0e,0x0f }; + +CK_MECHANISM aeskeygen_mech = { CKM_AES_KEY_GEN, NULL, 0 }; +CK_MECHANISM endecrypt_mech = { CKM_AES_CBC, aes_iv, sizeof(aes_iv) }; +CK_MECHANISM signver_mech = { CKM_SHA256_HMAC, NULL, 0 }; +CK_MECHANISM mackeygen_mech = { CKM_GENERIC_SECRET_KEY_GEN, NULL, 0 }; +CK_MECHANISM digest_mech = { CKM_SHA256, NULL, 0 }; + +CK_BYTE data1[512]; +CK_BYTE data2[512]; + + +CK_RV do_digest_encrypt_decrypt_digest(void) +{ + CK_SESSION_HANDLE session; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len; + CK_RV rc = CKR_OK, loc_rc; + CK_FLAGS flags; + CK_OBJECT_HANDLE aes_key = CK_INVALID_HANDLE; + CK_BYTE encrypted1[sizeof(data1) + 16]; + CK_ULONG encrypted1_len; + CK_BYTE encrypted2[sizeof(data2) + 16]; + CK_ULONG encrypted2_len; + CK_BYTE encrypted3[16]; + CK_ULONG encrypted3_len; + CK_BYTE clear[sizeof(data1) + 16]; + CK_ULONG clear_len; + CK_BYTE digest1[32]; + CK_ULONG digest1_len; + CK_BYTE digest2[32]; + CK_ULONG digest2_len; + + testcase_begin("C_DigestEncryptUpdate with %s/%s", + mech_to_str(digest_mech.mechanism), + mech_to_str(endecrypt_mech.mechanism)); + + testcase_rw_session(); + testcase_user_login(); + + if (!mech_supported(SLOT_ID, digest_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(digest_mech.mechanism), + (unsigned int)digest_mech.mechanism); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, endecrypt_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(endecrypt_mech.mechanism), + (unsigned int)endecrypt_mech.mechanism); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, aeskeygen_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism); + goto testcase_cleanup; + } + + /* generate an AES key */ + rc = generate_AESKey(session, 256 / 8, CK_TRUE, &aeskeygen_mech, &aes_key); + if (rc != CKR_OK) { + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("generate key with mech %s (%u) in slot %lu " + "is not allowed by policy", + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism, + SLOT_ID); + rc = CKR_OK; + goto testcase_cleanup; + } + + testcase_error("generate key with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + testcase_new_assertion(); + + /* Initialize operations */ + rc = funcs->C_EncryptInit(session, &endecrypt_mech, aes_key); + if (rc != CKR_OK) { + testcase_error("C_EncryptInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(endecrypt_mech.mechanism), + (unsigned int)endecrypt_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = funcs->C_DigestInit(session, &digest_mech); + if (rc != CKR_OK) { + testcase_error("C_DigestInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(digest_mech.mechanism), + (unsigned int)digest_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* First chunk */ + encrypted1_len = 0; + rc = funcs->C_DigestEncryptUpdate(session, data1, sizeof(data1), + NULL, &encrypted1_len); + if (rc != CKR_OK) { + testcase_error("C_DigestEncryptUpdate (1) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted1_len < sizeof(data1)) { + testcase_error("Wrong encrypted length from C_DigestEncryptUpdate (1): %lu", + encrypted1_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + encrypted1_len = sizeof(encrypted1); + rc = funcs->C_DigestEncryptUpdate(session, data1, sizeof(data1), + encrypted1, &encrypted1_len); + if (rc != CKR_OK) { + testcase_error("C_DigestEncryptUpdate (2) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted1_len != sizeof(data1)) { + testcase_error("Wrong encrypted length from C_DigestEncryptUpdate (2): %lu", + encrypted1_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Second chunk */ + encrypted2_len = 0; + rc = funcs->C_DigestEncryptUpdate(session, data2, sizeof(data2), + NULL, &encrypted2_len); + if (rc != CKR_OK) { + testcase_error("C_DigestEncryptUpdate (3) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted2_len < sizeof(data2)) { + testcase_error("Wrong encrypted length from C_DigestEncryptUpdate (3): %lu", + encrypted2_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + encrypted2_len = sizeof(encrypted2); + rc = funcs->C_DigestEncryptUpdate(session, data2, sizeof(data2), + encrypted2, &encrypted2_len); + if (rc != CKR_OK) { + testcase_error("C_DigestEncryptUpdate (4) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted2_len != sizeof(data2)) { + testcase_error("Wrong encrypted length from C_DigestEncryptUpdate (4): %lu", + encrypted2_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Finalize operations */ + encrypted3_len = sizeof(encrypted3); + rc = funcs->C_EncryptFinal(session, encrypted3, &encrypted3_len); + if (rc != CKR_OK) { + testcase_error("C_EncryptFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted3_len != 0) { + testcase_error("Wrong encrypted length from C_EncryptFinal: %lu", + encrypted3_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + digest1_len = sizeof(digest1); + rc = funcs->C_DigestFinal(session, digest1, &digest1_len); + if (rc != CKR_OK) { + testcase_error("C_DigestFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + testcase_pass("C_DigestEncryptUpdate with %s/%s", + mech_to_str(digest_mech.mechanism), + mech_to_str(endecrypt_mech.mechanism)); + + testcase_begin("C_DecryptDigestUpdate with %s/%s", + mech_to_str(endecrypt_mech.mechanism), + mech_to_str(digest_mech.mechanism)); + + testcase_new_assertion(); + + /* Initialize operations */ + rc = funcs->C_DecryptInit(session, &endecrypt_mech, aes_key); + if (rc != CKR_OK) { + testcase_error("C_DecryptInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(endecrypt_mech.mechanism), + (unsigned int)endecrypt_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = funcs->C_DigestInit(session, &digest_mech); + if (rc != CKR_OK) { + testcase_error("C_DigestInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(digest_mech.mechanism), + (unsigned int)digest_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* First chunk */ + clear_len = 0; + rc = funcs->C_DecryptDigestUpdate(session, encrypted1, encrypted1_len, + NULL, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptDigestUpdate (1) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len < sizeof(data1)) { + testcase_error("Wrong encrypted length from C_DecryptDigestUpdate (1): %lu", + clear_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + clear_len = sizeof(clear); + rc = funcs->C_DecryptDigestUpdate(session, encrypted1, encrypted1_len, + clear, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptDigestUpdate (2) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len != sizeof(data1)) { + testcase_error("Wrong encrypted length from C_DecryptDigestUpdate (2): %lu", + encrypted1_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + if (memcmp(clear, data1, clear_len) != 0) { + testcase_error("Wrong decrypted data from C_DecryptDigestUpdate (2)"); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Second chunk */ + clear_len = 0; + rc = funcs->C_DecryptDigestUpdate(session, encrypted2, encrypted2_len, + NULL, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptDigestUpdate (3) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len < sizeof(data2)) { + testcase_error("Wrong encrypted length from C_DecryptDigestUpdate (3): %lu", + clear_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + clear_len = sizeof(clear); + rc = funcs->C_DecryptDigestUpdate(session, encrypted2, encrypted2_len, + clear, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptDigestUpdate (4) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len != sizeof(data2)) { + testcase_error("Wrong encrypted length from C_DecryptDigestUpdate (4): %lu", + encrypted1_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + if (memcmp(clear, data2, clear_len) != 0) { + testcase_error("Wrong decrypted data from C_DecryptDigestUpdate (4)"); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Finalize operations */ + clear_len = sizeof(clear); + rc = funcs->C_DecryptFinal(session, clear, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len != 0) { + testcase_error("Wrong encrypted length from C_DecryptFinal: %lu", + clear_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + digest2_len = sizeof(digest2); + rc = funcs->C_DigestFinal(session, digest2, &digest2_len); + if (rc != CKR_OK) { + testcase_error("C_DigestFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (digest1_len != digest2_len) { + testcase_error("Wrong encrypted length from C_DigestFinal: %lu", + digest2_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + if (memcmp(digest1, digest2, digest1_len) != 0) { + testcase_error("Wrong digest from C_DigestFinal"); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + testcase_pass("C_DecryptDigestUpdate with %s/%s", + mech_to_str(endecrypt_mech.mechanism), + mech_to_str(digest_mech.mechanism)); + +testcase_cleanup: + if (aes_key != CK_INVALID_HANDLE) { + loc_rc = funcs->C_DestroyObject(session, aes_key); + if (loc_rc != CKR_OK) + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(loc_rc)); + } + + testcase_user_logout(); + rc = funcs->C_CloseAllSessions(SLOT_ID); + if (rc != CKR_OK) { + testcase_error("C_CloseAllSessions rc=%s", p11_get_ckr(rc)); + } + + return rc; +} + +CK_RV do_sign_encrypt_decrypt_verify(void) +{ + CK_SESSION_HANDLE session; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len; + CK_RV rc = CKR_OK, loc_rc; + CK_FLAGS flags; + CK_OBJECT_HANDLE aes_key = CK_INVALID_HANDLE; + CK_OBJECT_HANDLE mac_key = CK_INVALID_HANDLE; + CK_BYTE encrypted1[sizeof(data1) + 16]; + CK_ULONG encrypted1_len; + CK_BYTE encrypted2[sizeof(data2) + 16]; + CK_ULONG encrypted2_len; + CK_BYTE encrypted3[16]; + CK_ULONG encrypted3_len; + CK_BYTE clear[sizeof(data1) + 16]; + CK_ULONG clear_len; + CK_BYTE signature[32]; + CK_ULONG signature_len; + + testcase_begin("C_SignEncryptUpdate with %s/%s", + mech_to_str(signver_mech.mechanism), + mech_to_str(endecrypt_mech.mechanism)); + + testcase_rw_session(); + testcase_user_login(); + + if (!mech_supported(SLOT_ID, signver_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(signver_mech.mechanism), + (unsigned int)signver_mech.mechanism); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, endecrypt_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(endecrypt_mech.mechanism), + (unsigned int)endecrypt_mech.mechanism); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, aeskeygen_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, mackeygen_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(mackeygen_mech.mechanism), + (unsigned int)mackeygen_mech.mechanism); + goto testcase_cleanup; + } + + /* generate an AES key */ + rc = generate_AESKey(session, 256 / 8, CK_TRUE, &aeskeygen_mech, &aes_key); + if (rc != CKR_OK) { + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("generate key with mech %s (%u) in slot %lu " + "is not allowed by policy", + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism, + SLOT_ID); + rc = CKR_OK; + goto testcase_cleanup; + } + + testcase_error("generate key with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* generate a MAC key */ + rc = generate_SecretKey(session, 256, &mackeygen_mech, &mac_key); + if (rc != CKR_OK) { + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("generate key with mech %s (%u) in slot %lu " + "is not allowed by policy", + mech_to_str(mackeygen_mech.mechanism), + (unsigned int)mackeygen_mech.mechanism, + SLOT_ID); + rc = CKR_OK; + goto testcase_cleanup; + } + + testcase_error("generate key with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(mackeygen_mech.mechanism), + (unsigned int)mackeygen_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + testcase_new_assertion(); + + /* Initialize operations */ + rc = funcs->C_EncryptInit(session, &endecrypt_mech, aes_key); + if (rc != CKR_OK) { + testcase_error("C_EncryptInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(endecrypt_mech.mechanism), + (unsigned int)endecrypt_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = funcs->C_SignInit(session, &signver_mech, mac_key); + if (rc != CKR_OK) { + testcase_error("C_SignInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(signver_mech.mechanism), + (unsigned int)signver_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* First chunk */ + encrypted1_len = 0; + rc = funcs->C_SignEncryptUpdate(session, data1, sizeof(data1), + NULL, &encrypted1_len); + if (rc != CKR_OK) { + testcase_error("C_SignEncryptUpdate (1) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted1_len < sizeof(data1)) { + testcase_error("Wrong encrypted length from C_SignEncryptUpdate (1): %lu", + encrypted1_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + encrypted1_len = sizeof(encrypted1); + rc = funcs->C_SignEncryptUpdate(session, data1, sizeof(data1), + encrypted1, &encrypted1_len); + if (rc != CKR_OK) { + testcase_error("C_SignEncryptUpdate (2) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted1_len != sizeof(data1)) { + testcase_error("Wrong encrypted length from C_SignEncryptUpdate (2): %lu", + encrypted1_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Second chunk */ + encrypted2_len = 0; + rc = funcs->C_SignEncryptUpdate(session, data2, sizeof(data2), + NULL, &encrypted2_len); + if (rc != CKR_OK) { + testcase_error("C_SignEncryptUpdate (3) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted2_len < sizeof(data2)) { + testcase_error("Wrong encrypted length from C_SignEncryptUpdate (3): %lu", + encrypted2_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + encrypted2_len = sizeof(encrypted2); + rc = funcs->C_SignEncryptUpdate(session, data2, sizeof(data2), + encrypted2, &encrypted2_len); + if (rc != CKR_OK) { + testcase_error("C_SignEncryptUpdate (4) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted2_len != sizeof(data2)) { + testcase_error("Wrong encrypted length from C_SignEncryptUpdate (4): %lu", + encrypted2_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Finalize operations */ + encrypted3_len = sizeof(encrypted3); + rc = funcs->C_EncryptFinal(session, encrypted3, &encrypted3_len); + if (rc != CKR_OK) { + testcase_error("C_EncryptFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted3_len != 0) { + testcase_error("Wrong encrypted length from C_EncryptFinal: %lu", + encrypted3_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + signature_len = sizeof(signature); + rc = funcs->C_SignFinal(session, signature, &signature_len); + if (rc != CKR_OK) { + testcase_error("C_SignFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + testcase_pass("C_SignEncryptUpdate with %s/%s", + mech_to_str(signver_mech.mechanism), + mech_to_str(endecrypt_mech.mechanism)); + + testcase_begin("C_DecryptVerifyUpdate with %s/%s", + mech_to_str(endecrypt_mech.mechanism), + mech_to_str(signver_mech.mechanism)); + + testcase_new_assertion(); + + /* Initialize operations */ + rc = funcs->C_DecryptInit(session, &endecrypt_mech, aes_key); + if (rc != CKR_OK) { + testcase_error("C_DecryptInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(endecrypt_mech.mechanism), + (unsigned int)endecrypt_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = funcs->C_VerifyInit(session, &signver_mech, mac_key); + if (rc != CKR_OK) { + testcase_error("C_VerifyInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(digest_mech.mechanism), + (unsigned int)signver_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* First chunk */ + clear_len = 0; + rc = funcs->C_DecryptVerifyUpdate(session, encrypted1, encrypted1_len, + NULL, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptVerifyUpdate (1) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len < sizeof(data1)) { + testcase_error("Wrong encrypted length from C_DecryptVerifyUpdate (1): %lu", + clear_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + clear_len = sizeof(clear); + rc = funcs->C_DecryptVerifyUpdate(session, encrypted1, encrypted1_len, + clear, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptVerifyUpdate (2) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len != sizeof(data1)) { + testcase_error("Wrong encrypted length from C_DecryptVerifyUpdate (2): %lu", + encrypted1_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + if (memcmp(clear, data1, clear_len) != 0) { + testcase_error("Wrong decrypted data from C_DecryptVerifyUpdate (2)"); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Second chunk */ + clear_len = 0; + rc = funcs->C_DecryptVerifyUpdate(session, encrypted2, encrypted2_len, + NULL, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptVerifyUpdate (3) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len < sizeof(data2)) { + testcase_error("Wrong encrypted length from C_DecryptVerifyUpdate (3): %lu", + clear_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + clear_len = sizeof(clear); + rc = funcs->C_DecryptVerifyUpdate(session, encrypted2, encrypted2_len, + clear, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptVerifyUpdate (4) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len != sizeof(data2)) { + testcase_error("Wrong encrypted length from C_DecryptVerifyUpdate (4): %lu", + encrypted1_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + if (memcmp(clear, data2, clear_len) != 0) { + testcase_error("Wrong decrypted data from C_DecryptVerifyUpdate (4)"); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Finalize operations */ + clear_len = sizeof(clear); + rc = funcs->C_DecryptFinal(session, clear, &clear_len); + if (rc != CKR_OK) { + testcase_error("C_DecryptFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (clear_len != 0) { + testcase_error("Wrong encrypted length from C_DecryptFinal: %lu", + clear_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + rc = funcs->C_VerifyFinal(session, signature, signature_len); + if (rc != CKR_OK) { + testcase_error("C_VerifyFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + testcase_pass("C_DecryptVerifyUpdate with %s/%s", + mech_to_str(endecrypt_mech.mechanism), + mech_to_str(signver_mech.mechanism)); + +testcase_cleanup: + if (aes_key != CK_INVALID_HANDLE) { + loc_rc = funcs->C_DestroyObject(session, aes_key); + if (loc_rc != CKR_OK) + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(loc_rc)); + } + if (mac_key != CK_INVALID_HANDLE) { + loc_rc = funcs->C_DestroyObject(session, mac_key); + if (loc_rc != CKR_OK) + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(loc_rc)); + } + + testcase_user_logout(); + rc = funcs->C_CloseAllSessions(SLOT_ID); + if (rc != CKR_OK) { + testcase_error("C_CloseAllSessions rc=%s", p11_get_ckr(rc)); + } + + return rc; + +} + +CK_RV do_save_restore_dual_state(void) +{ + CK_SESSION_HANDLE session; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len; + CK_RV rc = CKR_OK, loc_rc; + CK_FLAGS flags; + CK_OBJECT_HANDLE aes_key = CK_INVALID_HANDLE; + CK_BYTE encrypted1[sizeof(data1) + 16]; + CK_ULONG encrypted1_len; + CK_BYTE encrypted2[sizeof(data2) + 16]; + CK_ULONG encrypted2_len; + CK_BYTE encrypted2a[sizeof(data2) + 16]; + CK_ULONG encrypted2a_len; + CK_BYTE encrypted3[16]; + CK_ULONG encrypted3_len; + CK_BYTE digest1[32]; + CK_ULONG digest1_len; + CK_BYTE digest2[32]; + CK_ULONG digest2_len; + CK_BYTE *state = NULL; + CK_ULONG state_len; + + testcase_begin("Save/Restore state with 2 active operations"); + + testcase_rw_session(); + testcase_user_login(); + + if (!mech_supported(SLOT_ID, digest_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(digest_mech.mechanism), + (unsigned int)digest_mech.mechanism); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, endecrypt_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(endecrypt_mech.mechanism), + (unsigned int)endecrypt_mech.mechanism); + goto testcase_cleanup; + } + if (!mech_supported(SLOT_ID, aeskeygen_mech.mechanism)) { + testcase_skip("Slot %u doesn't support %s (0x%x)", + (unsigned int)SLOT_ID, + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism); + goto testcase_cleanup; + } + + /* generate an AES key */ + rc = generate_AESKey(session, 256 / 8, CK_TRUE, &aeskeygen_mech, &aes_key); + if (rc != CKR_OK) { + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("generate key with mech %s (%u) in slot %lu " + "is not allowed by policy", + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism, + SLOT_ID); + rc = CKR_OK; + goto testcase_cleanup; + } + + testcase_error("generate key with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(aeskeygen_mech.mechanism), + (unsigned int)aeskeygen_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* Initialize operations */ + rc = funcs->C_EncryptInit(session, &endecrypt_mech, aes_key); + if (rc != CKR_OK) { + testcase_error("C_EncryptInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(endecrypt_mech.mechanism), + (unsigned int)endecrypt_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = funcs->C_DigestInit(session, &digest_mech); + if (rc != CKR_OK) { + testcase_error("C_DigestInit with mech %s (%u) in slot %lu failed, rc=%s", + mech_to_str(digest_mech.mechanism), + (unsigned int)digest_mech.mechanism, + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* First chunk */ + encrypted1_len = sizeof(encrypted1); + rc = funcs->C_DigestEncryptUpdate(session, data1, sizeof(data1), + encrypted1, &encrypted1_len); + if (rc != CKR_OK) { + testcase_error("C_DigestEncryptUpdate (2) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* Save state of both operations */ + rc = funcs->C_GetOperationState(session, NULL, &state_len); + if (rc != CKR_OK) { + if (rc == CKR_STATE_UNSAVEABLE) { + testcase_skip("Operation state is not savable"); + goto testcase_cleanup; + } + + testcase_error("C_GetOperationState (1) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + state = calloc(1, state_len); + if (state == NULL) { + testcase_fail("malloc for state buffer of size %lu failed", state_len); + rc = CKR_HOST_MEMORY; + goto testcase_cleanup; + } + + rc = funcs->C_GetOperationState(session, state, &state_len); + if (rc != CKR_OK) { + if (rc == CKR_STATE_UNSAVEABLE) { + testcase_skip("Operation state is not savable"); + goto testcase_cleanup; + } + + testcase_error("C_GetOperationState (2) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* Second chunk */ + encrypted2_len = sizeof(encrypted2); + rc = funcs->C_DigestEncryptUpdate(session, data2, sizeof(data2), + encrypted2, &encrypted2_len); + if (rc != CKR_OK) { + testcase_error("C_DigestEncryptUpdate (4) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* Finalize operations */ + encrypted3_len = sizeof(encrypted3); + rc = funcs->C_EncryptFinal(session, encrypted3, &encrypted3_len); + if (rc != CKR_OK) { + testcase_error("C_EncryptFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + digest1_len = sizeof(digest1); + rc = funcs->C_DigestFinal(session, digest1, &digest1_len); + if (rc != CKR_OK) { + testcase_error("C_DigestFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + testcase_new_assertion(); + + /* restore state from after first chunk */ + rc = funcs->C_SetOperationState(session, state, state_len, + aes_key, CK_INVALID_HANDLE); + if (rc != CKR_OK) { + testcase_error("C_SetOperationState in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* Second chunk again */ + encrypted2a_len = sizeof(encrypted2a); + rc = funcs->C_DigestEncryptUpdate(session, data2, sizeof(data2), + encrypted2a, &encrypted2a_len); + if (rc != CKR_OK) { + testcase_error("C_DigestEncryptUpdate (5) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (encrypted2a_len != encrypted2_len) { + testcase_error("Wrong encrypted length from C_DigestEncryptUpdate (5): %lu", + encrypted2a_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + if (memcmp(encrypted2, encrypted2a, encrypted2_len) != 0) { + testcase_error("Wrong encrypted data from C_DigestEncryptUpdate (5)"); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + /* Finalize operations again */ + encrypted3_len = sizeof(encrypted3); + rc = funcs->C_EncryptFinal(session, encrypted3, &encrypted3_len); + if (rc != CKR_OK) { + testcase_error("C_EncryptFinal in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + digest2_len = sizeof(digest2); + rc = funcs->C_DigestFinal(session, digest2, &digest2_len); + if (rc != CKR_OK) { + testcase_error("C_DigestFinal (2) in slot %lu failed, rc=%s", + SLOT_ID, p11_get_ckr(rc)); + goto testcase_cleanup; + } + + if (digest1_len != digest2_len) { + testcase_error("Wrong encrypted length from C_DigestFinal (2): %lu", + digest2_len); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + if (memcmp(digest1, digest2, digest1_len) != 0) { + testcase_error("Wrong digest from C_DigestFinal (2)"); + rc = CKR_FUNCTION_FAILED; + goto testcase_cleanup; + } + + testcase_pass("Save/Restore state with 2 active operations"); + +testcase_cleanup: + if (aes_key != CK_INVALID_HANDLE) { + loc_rc = funcs->C_DestroyObject(session, aes_key); + if (loc_rc != CKR_OK) + testcase_error("C_DestroyObject(), rc=%s.", p11_get_ckr(loc_rc)); + } + + testcase_user_logout(); + rc = funcs->C_CloseAllSessions(SLOT_ID); + if (rc != CKR_OK) { + testcase_error("C_CloseAllSessions rc=%s", p11_get_ckr(rc)); + } + + if (state != NULL) + free(state); + + return rc; + +} + +CK_RV do_dual_functions_tests(void) +{ + CK_RV rc = CKR_OK; + + rc |= do_digest_encrypt_decrypt_digest(); + + rc |= do_sign_encrypt_decrypt_verify(); + + rc |= do_save_restore_dual_state(); + + return rc; +} + + +int main(int argc, char **argv) +{ + int rc; + CK_C_INITIALIZE_ARGS cinit_args; + CK_RV rv = 0; + CK_ULONG i; + + rc = do_ParseArgs(argc, argv); + if (rc != 1) + return rc; + + printf("Using slot #%lu...\n\n", SLOT_ID); + + rc = do_GetFunctionList(); + if (!rc) { + testcase_error("do_getFunctionList(), rc=%s", p11_get_ckr(rc)); + return rc; + } + + memset(&cinit_args, 0x0, sizeof(cinit_args)); + cinit_args.flags = CKF_OS_LOCKING_OK; + funcs->C_Initialize(&cinit_args); + + testcase_setup(); + + for (i = 0; i < sizeof(data1); i++) + data1[i] = i; + for (i = 0; i < sizeof(data1); i++) + data2[i] = 255 - i; + + rv = do_dual_functions_tests(); + if (rv != CKR_OK) + goto finalize; + + rv = funcs->C_Finalize(NULL); + if (rv != CKR_OK) { + testcase_fail("C_Finalize rc = %s", p11_get_ckr(rv)); + goto out; + } + + rv = 0; + goto out; + +finalize: + rv = funcs->C_Finalize(NULL); + if (rv != CKR_OK) { + testcase_fail("C_Finalize rc = %s", p11_get_ckr(rv)); + rv = 1; + } +out: + testcase_print_result(); + return testcase_return(rv); +} diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/misc_tests.mk opencryptoki-3.20.0+dfsg/testcases/misc_tests/misc_tests.mk --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/misc_tests.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/misc_tests.mk 2023-02-13 09:22:42.000000000 +0100 @@ -8,7 +8,7 @@ testcases/misc_tests/obj_lock testcases/misc_tests/tok2tok_transport \ testcases/misc_tests/obj_lock testcases/misc_tests/reencrypt \ testcases/misc_tests/cca_export_import_test \ - testcases/misc_tests/events + testcases/misc_tests/events testcases/misc_tests/dual_functions testcases_misc_tests_obj_mgmt_tests_CFLAGS = ${testcases_inc} testcases_misc_tests_obj_mgmt_tests_LDADD = \ @@ -79,3 +79,8 @@ testcases_misc_tests_events_LDADD = testcases/common/libcommon.la testcases_misc_tests_events_SOURCES = testcases/misc_tests/events.c \ usr/lib/common/event_client.c + +testcases_misc_tests_dual_functions_CFLAGS = ${testcases_inc} +testcases_misc_tests_dual_functions_LDADD = testcases/common/libcommon.la +testcases_misc_tests_dual_functions_SOURCES = \ + testcases/misc_tests/dual_functions.c diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/obj_mgmt.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/obj_mgmt.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/obj_mgmt.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/obj_mgmt.c 2023-02-13 09:22:42.000000000 +0100 @@ -796,7 +796,7 @@ } if (find_count != 1) { - testcase_fail("found %ld instead of just 1 object", find_count); + testcase_fail("found %lu instead of just 1 object", find_count); return -1; } @@ -825,7 +825,7 @@ } if (find_count != 0) { - testcase_fail("found %ld objects when none where expected", find_count); + testcase_fail("found %lu objects when none where expected", find_count); return -1; } @@ -849,7 +849,7 @@ } if (find_count != num_existing_objects + 3) { - testcase_fail("found %ld instead of %ld objects", find_count, + testcase_fail("found %lu instead of %lu objects", find_count, num_existing_objects + 3); return -1; } @@ -1053,7 +1053,7 @@ } if (find_count != 3) { - testcase_fail("found %ld objects instead of expected 3", find_count); + testcase_fail("found %lu objects instead of expected 3", find_count); return -1; } @@ -1077,7 +1077,7 @@ } if (find_count != 1) { - testcase_fail("found %ld objects instead of expected 1", find_count); + testcase_fail("found %lu objects instead of expected 1", find_count); return -1; } @@ -1106,7 +1106,7 @@ } if (find_count != 0) { - testcase_fail("found %ld objects when none where expected", find_count); + testcase_fail("found %lu objects when none where expected", find_count); return -1; } @@ -1151,7 +1151,7 @@ } if (find_count != 3) { - testcase_fail("found %ld objects instead of expected 3", find_count); + testcase_fail("found %lu objects instead of expected 3", find_count); return -1; } @@ -1175,7 +1175,7 @@ } if (find_count != 1) { - testcase_fail("found %ld objects instead of expected 1", find_count); + testcase_fail("found %lu objects instead of expected 1", find_count); return -1; } @@ -1204,7 +1204,7 @@ } if (find_count != 0) { - testcase_fail("found %ld objects when none where expected", find_count); + testcase_fail("found %lu objects when none where expected", find_count); return -1; } @@ -1247,7 +1247,7 @@ } if (find_count != 0) { - testcase_fail("found %ld objects when none where expected", find_count); + testcase_fail("found %lu objects when none where expected", find_count); return -1; } @@ -1453,7 +1453,7 @@ * feature object */ if (find_count != 2) { - testcase_fail("found %ld objects when expected 2", find_count); + testcase_fail("found %lu objects when expected 2", find_count); rc = -1; goto destroy; } @@ -1490,7 +1490,7 @@ } if (find_count != 1) { - testcase_fail("found %ld objects when expected 1", find_count); + testcase_fail("found %lu objects when expected 1", find_count); funcs->C_FindObjectsFinal(h_session); rc = -1; goto destroy; @@ -1642,7 +1642,7 @@ goto destroy; } if (find_count != 2) { - testcase_fail("found %ld objects when expected 1", find_count); + testcase_fail("found %lu objects when expected 1", find_count); funcs->C_FindObjectsFinal(h_session); rc = -1; goto destroy; @@ -1671,7 +1671,7 @@ goto destroy; } if (find_count != 1) { - testcase_fail("found %ld objects when expected 1", find_count); + testcase_fail("found %lu objects when expected 1", find_count); funcs->C_FindObjectsFinal(h_session); rc = -1; goto destroy; @@ -1713,7 +1713,7 @@ return rc; } -CK_RV obj_mgmt_functions() +CK_RV obj_mgmt_functions(void) { int rc; diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/obj_mgmt_lock.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/obj_mgmt_lock.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/obj_mgmt_lock.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/obj_mgmt_lock.c 2023-02-13 09:22:42.000000000 +0100 @@ -699,7 +699,7 @@ } if (find_count != 0) { - testcase_fail("found %ld objects when none where expected", find_count); + testcase_fail("found %lu objects when none where expected", find_count); rc = -1; goto destroy; } @@ -944,7 +944,7 @@ } if (find_count != 0) { - testcase_fail("found %ld objects when none where expected", find_count); + testcase_fail("found %lu objects when none where expected", find_count); rc = -1; goto destroy; } @@ -1018,7 +1018,7 @@ } if (find_count != 0) { - testcase_fail("found %ld objects when none where expected", find_count); + testcase_fail("found %lu objects when none where expected", find_count); rc = -1; goto destroy; } @@ -1270,7 +1270,7 @@ return rc; } -CK_RV obj_mgmt_functions() +CK_RV obj_mgmt_functions(void) { int rc, errors = 0; diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/p11sak_test.sh opencryptoki-3.20.0+dfsg/testcases/misc_tests/p11sak_test.sh --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/p11sak_test.sh 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/p11sak_test.sh 2023-02-13 09:22:42.000000000 +0100 @@ -12,6 +12,7 @@ # # sudo -E ./p11sak_test.sh +status=0 echo "** Now executing 'p11sak_test.sh'" @@ -28,12 +29,24 @@ P11SAK_AES_PRE=p11sak-aes-pre.out P11SAK_AES_LONG=p11sak-aes-long.out P11SAK_AES_POST=p11sak-aes-post.out +P11SAK_AES_XTS_PRE=p11sak-aes-xts-pre.out +P11SAK_AES_XTS_LONG=p11sak-aes-xts-long.out +P11SAK_AES_XTS_POST=p11sak-aes-xts-post.out P11SAK_RSA_PRE=p11sak-rsa-pre.out P11SAK_RSA_LONG=p11sak-rsa-long.out P11SAK_RSA_POST=p11sak-rsa-post.out P11SAK_EC_PRE=p11sak-ec-pre.out P11SAK_EC_LONG=p11sak-ec-long.out P11SAK_EC_POST=p11sak-ec-post.out +P11SAK_IBM_DIL_PRE=p11sak-ibm-dil-pre.out +P11SAK_IBM_DIL_LONG=p11sak-ibm-dil-long.out +P11SAK_IBM_DIL_POST=p11sak-ibm-dil-post.out +P11SAK_IBM_KYBER_PRE=p11sak-ibm-kyber-pre.out +P11SAK_IBM_KYBER_LONG=p11sak-ibm-kyber-long.out +P11SAK_IBM_KYBER_POST=p11sak-ibm-kyber-post.out +P11SAK_ALL_PINOPT=p11sak-all-pinopt +P11SAK_ALL_PINENV=p11sak-all-pinenv +P11SAK_ALL_PINCON=p11sak-all-pincon echo "** Setting SLOT=30 to the Softtoken unless otherwise set - 'p11sak_test.sh'" @@ -51,13 +64,24 @@ # generate objects # des -p11sak generate-key des --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-des +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_DES_KEY_GEN) ]]; then + p11sak generate-key des --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-des +else + echo "Skip generating des keys, slot does not support CKM_DES_KEY_GEN" +fi # 3des p11sak generate-key 3des --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-3des # aes [128 | 192 | 256] p11sak generate-key aes 128 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-128 p11sak generate-key aes 192 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-192 p11sak generate-key aes 256 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-256 +# aes-xts [128 | 256] +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_AES_XTS_KEY_GEN) && -z $( pkcsconf -t -c $SLOT | grep "Model: EP11") ]]; then + p11sak generate-key aes-xts 128 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-xts-128 + p11sak generate-key aes-xts 256 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-xts-256 +else + echo "Skip generating aes-xts keys, slot does not support CKM_AES_XTS_KEY_GEN" +fi # rsa [1024 | 2048 | 4096] p11sak generate-key rsa 1024 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-rsa-1024 p11sak generate-key rsa 2048 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-rsa-2048 @@ -66,6 +90,18 @@ p11sak generate-key ec prime256v1 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ec-prime256v1 p11sak generate-key ec secp384r1 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ec-secp384r1 p11sak generate-key ec secp521r1 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ec-secp521r1 +# ibm-dilithium +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_IBM_DILITHIUM) ]]; then + p11sak generate-key ibm-dilithium r2_65 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ibm-dilithium +else + echo "Skip generating ibm-dilithium keys, slot does not support CKM_IBM_DILITHIUM" +fi +# ibm-kyber +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_IBM_KYBER) ]]; then + p11sak generate-key ibm-kyber r2_1024 --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ibm-kyber +else + echo "Skip generating ibm-kyber keys, slot does not support CKM_IBM_KYBER" +fi echo "** Now list keys and redirect output to pre-files - 'p11sak_test.sh'" @@ -75,14 +111,26 @@ p11sak list-key des --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_DES_PRE p11sak list-key 3des --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_3DES_PRE p11sak list-key aes --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_AES_PRE +p11sak list-key aes-xts --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_AES_XTS_PRE p11sak list-key rsa --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_RSA_PRE p11sak list-key ec --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_EC_PRE +p11sak list-key ibm-dilithium --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_IBM_DIL_PRE p11sak list-key des --slot $SLOT --pin $PKCS11_USER_PIN --long &> $P11SAK_DES_LONG p11sak list-key 3des --slot $SLOT --pin $PKCS11_USER_PIN --long &> $P11SAK_3DES_LONG p11sak list-key aes --slot $SLOT --pin $PKCS11_USER_PIN --long &> $P11SAK_AES_LONG +p11sak list-key aes-xts --slot $SLOT --pin $PKCS11_USER_PIN --long &> $P11SAK_AES_XTS_LONG p11sak list-key rsa --slot $SLOT --pin $PKCS11_USER_PIN --long &> $P11SAK_RSA_LONG p11sak list-key ec --slot $SLOT --pin $PKCS11_USER_PIN --long &> $P11SAK_EC_LONG +p11sak list-key ibm-dilithium --slot $SLOT --pin $PKCS11_USER_PIN --long &> $P11SAK_IBM_DIL_LONG +p11sak list-key ibm-kyber --slot $SLOT --pin $PKCS11_USER_PIN --long &> $P11SAK_IBM_KYBER_LONG + +p11sak list-key all --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_ALL_PINOPT +RC_P11SAK_PINOPT=$? +p11sak list-key all --slot $SLOT &> $P11SAK_ALL_PINENV +RC_P11SAK_PINENV=$? +printf "${PKCS11_USER_PIN}\n" | p11sak list-key all --slot $SLOT --force-pin-prompt | tail -n +2 &> $P11SAK_ALL_PINCON +RC_P11SAK_PINCON=$? echo "** Now remove keys - 'p11sak_test.sh'" @@ -96,6 +144,9 @@ p11sak remove-key aes --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-128 -f p11sak remove-key aes --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-192 -f p11sak remove-key aes --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-256 -f +# aes-xts [128 | 256] +p11sak remove-key aes-xts --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-xts-128 -f +p11sak remove-key aes-xts --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-aes-xts-256 -f # rsa [1024 | 2048 | 4096] # remove public key p11sak remove-key rsa --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-rsa-1024:pub -f @@ -114,6 +165,12 @@ p11sak remove-key ec --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ec-prime256v1:prv -f p11sak remove-key ec --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ec-secp384r1:prv -f p11sak remove-key ec --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ec-secp521r1:prv -f +# remove ibm dilithium keys +p11sak remove-key ibm-dilithium --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ibm-dilithium:pub -f +p11sak remove-key ibm-dilithium --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ibm-dilithium:prv -f +# remove ibm kyber keys +p11sak remove-key ibm-kyber --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ibm-kyber:pub -f +p11sak remove-key ibm-kyber --slot $SLOT --pin $PKCS11_USER_PIN --label p11sak-ibm-kyber:prv -f echo "** Now list keys and rediirect to post-files - 'p11sak_test.sh'" @@ -123,47 +180,73 @@ p11sak list-key des --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_DES_POST p11sak list-key 3des --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_3DES_POST p11sak list-key aes --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_AES_POST +p11sak list-key aes-xts --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_AES_XTS_POST p11sak list-key rsa --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_RSA_POST p11sak list-key ec --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_EC_POST +p11sak list-key ibm-dilithium --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_IBM_DIL_POST +p11sak list-key ibm-kyber --slot $SLOT --pin $PKCS11_USER_PIN &> $P11SAK_IBM_KYBER_POST echo "** Now checking output files to determine PASS/FAIL of tests - 'p11sak_test.sh'" -# check DES -grep -q 'p11sak-des' $P11SAK_DES_PRE -rc=$? -if [ $rc = 0 ]; then -echo "* TESTCASE generate-key des PASS Generated random DES key" -else -echo "* TESTCASE generate-key des FAIL Failed to generate DES key" -fi -grep -v -q 'p11sak-des' $P11SAK_DES_POST -rc=$? -if [ $rc = 0 ]; then -echo "* TESTCASE remove-key des PASS Deleted generated DES key" -else -echo "* TESTCASE remove-key des FAIL Failed to delete generated DES key" -fi - - -# CK_BBOOL -if [[ $(grep -A 19 'p11sak-des' $P11SAK_DES_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "1" ]]; then -echo "* TESTCASE list-key des PASS Listed random des public keys CK_BBOOL attribute" -else -echo "* TESTCASE list-key des FAIL Failed to list des public keys CK_BBOOL attribute" -fi -# CK_ULONG -if [[ $(grep -A 19 'p11sak-des' $P11SAK_DES_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then -echo "* TESTCASE list-key des PASS Listed random des public keys CK_ULONG attribute" -else -echo "* TESTCASE list-key des FAIL Failed to list des public keys CK_ULONG attribute" -fi -# CK_BYTE -if [[ $(grep -A 19 'p11sak-des' $P11SAK_DES_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then -echo "* TESTCASE list-key des PASS Listed random des public keys CK_BYTE attribute" -else -echo "* TESTCASE list-key des FAIL Failed to list des public keys CK_BYTE attribute" +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_DES_KEY_GEN) ]]; then + # check DES + grep -q 'p11sak-des' $P11SAK_DES_PRE + rc=$? + if [ $rc = 0 ]; then + echo "* TESTCASE generate-key des PASS Generated random DES key" + else + echo "* TESTCASE generate-key des FAIL Failed to generate DES key" + status=1 + fi + grep -v -q 'p11sak-des' $P11SAK_DES_POST + rc=$? + if [ $rc = 0 ]; then + echo "* TESTCASE remove-key des PASS Deleted generated DES key" + else + echo "* TESTCASE remove-key des FAIL Failed to delete generated DES key" + status=1 + fi +else + echo "* TESTCASE generate-key des SKIP Generated random DES key" + echo "* TESTCASE remove-key des SKIP Deleted generated DES key" +fi + +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_DES_KEY_GEN) ]]; then + # CK_BBOOL + if [[ $(grep -A 20 'p11sak-des' $P11SAK_DES_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "1" ]]; then + echo "* TESTCASE list-key des PASS Listed random des public keys CK_BBOOL attribute" + else + echo "* TESTCASE list-key des FAIL Failed to list des public keys CK_BBOOL attribute" + status=1 + fi + # CK_ULONG + if [[ $(grep -A 20 'p11sak-des' $P11SAK_DES_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then + echo "* TESTCASE list-key des PASS Listed random des public keys CK_ULONG attribute" + else + echo "* TESTCASE list-key des FAIL Failed to list des public keys CK_ULONG attribute" + status=1 + fi + # CK_BYTE + if [[ $(grep -A 20 'p11sak-des' $P11SAK_DES_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then + echo "* TESTCASE list-key des PASS Listed random des public keys CK_BYTE attribute" + else + echo "* TESTCASE list-key des FAIL Failed to list des public keys CK_BYTE attribute" + status=1 + fi + # URI + if [[ $(grep -A 20 'p11sak-des' $P11SAK_DES_LONG | grep -c 'URI: pkcs11:.*type=secret-key') == "1" ]]; then + echo "* TESTCASE list-key des PASS list des key pkcs#11 URI" + else + echo "* TESTCASE list-key des FAIL list des key pkcs#11 URI" + status=1 + fi +else + echo "* TESTCASE list-key des SKIP Listed random des public keys CK_BBOOL attribute" + echo "* TESTCASE list-key des SKIP Listed random des public keys CK_ULONG attribute" + echo "* TESTCASE list-key des SKIP Listed random des public keys CK_BYTE attribute" + echo "* TESTCASE list-key des SKIP list des key pkcs#11 URI" fi @@ -171,36 +254,48 @@ grep -q 'p11sak-3des' $P11SAK_3DES_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key 3des PASS Generated random 3DES key" + echo "* TESTCASE generate-key 3des PASS Generated random 3DES key" else -echo "* TESTCASE generate-key 3des FAIL Failed to generate 3DES key" + echo "* TESTCASE generate-key 3des FAIL Failed to generate 3DES key" + status=1 fi grep -v -q 'p11sak-3des' $P11SAK_3DES_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key 3des PASS Deleted generated 3DES key" + echo "* TESTCASE remove-key 3des PASS Deleted generated 3DES key" else -echo "* TESTCASE remove-key 3des FAIL Failed to delete generated 3DES key" + echo "* TESTCASE remove-key 3des FAIL Failed to delete generated 3DES key" + status=1 fi # CK_BBOOL -if [[ $(grep -A 19 'p11sak-3des' $P11SAK_3DES_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "1" ]]; then -echo "* TESTCASE list-key 3des PASS Listed random 3des public keys CK_BBOOL attribute" +if [[ $(grep -A 23 'p11sak-3des' $P11SAK_3DES_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "1" ]]; then + echo "* TESTCASE list-key 3des PASS Listed random 3des public keys CK_BBOOL attribute" else -echo "* TESTCASE list-key 3des FAIL Failed to list 3des public keys CK_BBOOL attribute" + echo "* TESTCASE list-key 3des FAIL Failed to list 3des public keys CK_BBOOL attribute" + status=1 fi # CK_ULONG -if [[ $(grep -A 19 'p11sak-3des' $P11SAK_3DES_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then -echo "* TESTCASE list-key 3des PASS Listed random 3des public keys CK_ULONG attribute" +if [[ $(grep -A 23 'p11sak-3des' $P11SAK_3DES_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then + echo "* TESTCASE list-key 3des PASS Listed random 3des public keys CK_ULONG attribute" else -echo "* TESTCASE list-key 3des FAIL Failed to list 3des public keys CK_ULONG attribute" + echo "* TESTCASE list-key 3des FAIL Failed to list 3des public keys CK_ULONG attribute" + status=1 fi # CK_BYTE -if [[ $(grep -A 19 'p11sak-3des' $P11SAK_3DES_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then -echo "* TESTCASE list-key 3des PASS Listed random 3des public keys CK_BYTE attribute" +if [[ $(grep -A 23 'p11sak-3des' $P11SAK_3DES_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then + echo "* TESTCASE list-key 3des PASS Listed random 3des public keys CK_BYTE attribute" +else + echo "* TESTCASE list-key 3des FAIL Failed to list 3des public keys CK_BYTE attribute" + status=1 +fi +# URI +if [[ $(grep -A 23 'p11sak-3des' $P11SAK_3DES_LONG | grep -c 'URI: pkcs11:.*type=secret-key') == "1" ]]; then + echo "* TESTCASE list-key 3des PASS list 3des key pkcs#11 URI" else -echo "* TESTCASE list-key 3des FAIL Failed to list 3des public keys CK_BYTE attribute" + echo "* TESTCASE list-key 3des FAIL list 3des key pkcs#11 URI" + status=1 fi @@ -208,16 +303,18 @@ grep -q 'p11sak-aes-128' $P11SAK_AES_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key aes-128 PASS Generated random AES 128 key" + echo "* TESTCASE generate-key aes-128 PASS Generated random AES 128 key" else -echo "* TESTCASE generate-key aes-128 FAIL Failed to generate AES 128 key" + echo "* TESTCASE generate-key aes-128 FAIL Failed to generate AES 128 key" + status=1 fi grep -v -q 'p11sak-aes-128' $P11SAK_AES_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key aes-128 PASS Deleted generated AES 128 key" + echo "* TESTCASE remove-key aes-128 PASS Deleted generated AES 128 key" else -echo "* TESTCASE remove-key aes-128 FAIL Failed to delete generated AES 128 key" + echo "* TESTCASE remove-key aes-128 FAIL Failed to delete generated AES 128 key" + status=1 fi @@ -225,16 +322,18 @@ grep -q 'p11sak-aes-192' $P11SAK_AES_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key aes-192 PASS Generated random AES 192 key" + echo "* TESTCASE generate-key aes-192 PASS Generated random AES 192 key" else -echo "* TESTCASE generate-key aes-192 FAIL Failed to generate AES 192 key" + echo "* TESTCASE generate-key aes-192 FAIL Failed to generate AES 192 key" + status=1 fi grep -v -q 'p11sak-aes-192' $P11SAK_AES_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key aes-192 PASS Deleted generated AES 192 key" + echo "* TESTCASE remove-key aes-192 PASS Deleted generated AES 192 key" else -echo "* TESTCASE remove-key aes-192 FAIL Failed to delete generated AES 192 key" + echo "* TESTCASE remove-key aes-192 FAIL Failed to delete generated AES 192 key" + status=1 fi @@ -242,53 +341,142 @@ grep -q 'p11sak-aes-256' $P11SAK_AES_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key aes-256 PASS Generated random AES 256 key" + echo "* TESTCASE generate-key aes-256 PASS Generated random AES 256 key" else -echo "* TESTCASE generate-key aes-256 FAIL Failed to generate AES 256 key" + echo "* TESTCASE generate-key aes-256 FAIL Failed to generate AES 256 key" + status=1 fi grep -v -q 'p11sak-aes-256' $P11SAK_AES_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key aes-256 PASS Deleted generated AES 256 key" + echo "* TESTCASE remove-key aes-256 PASS Deleted generated AES 256 key" else -echo "* TESTCASE remove-key aes-256 FAIL Failed to delete generated AES 256 key" + echo "* TESTCASE remove-key aes-256 FAIL Failed to delete generated AES 256 key" + status=1 fi # CK_BBOOL -if [[ $(grep -A 57 'p11sak-aes-128' $P11SAK_AES_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "3" ]]; then -echo "* TESTCASE list-key aes PASS Listed random aes public keys CK_BBOOL attribute" +if [[ $(grep -A 69 'p11sak-aes-128' $P11SAK_AES_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "3" ]]; then + echo "* TESTCASE list-key aes PASS Listed random aes public keys CK_BBOOL attribute" else -echo "* TESTCASE list-key aes FAIL Failed to list aes public keys CK_BBOOL attribute" + echo "* TESTCASE list-key aes FAIL Failed to list aes public keys CK_BBOOL attribute" + status=1 fi # CK_ULONG -if [[ $(grep -A 57 'p11sak-aes-128' $P11SAK_AES_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then -echo "* TESTCASE list-key aes PASS Listed random aes public keys CK_ULONG attribute" +if [[ $(grep -A 69 'p11sak-aes-128' $P11SAK_AES_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then + echo "* TESTCASE list-key aes PASS Listed random aes public keys CK_ULONG attribute" else -echo "* TESTCASE list-key aes FAIL Failed to list aes public keys CK_ULONG attribute" + echo "* TESTCASE list-key aes FAIL Failed to list aes public keys CK_ULONG attribute" + status=1 fi # CK_BYTE -if [[ $(grep -A 57 'p11sak-aes-128' $P11SAK_AES_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then -echo "* TESTCASE list-key aes PASS Listed random aes public keys CK_BYTE attribute" +if [[ $(grep -A 69 'p11sak-aes-128' $P11SAK_AES_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then + echo "* TESTCASE list-key aes PASS Listed random aes public keys CK_BYTE attribute" else -echo "* TESTCASE list-key aes FAIL Failed to list aes public keys CK_BYTE attribute" + echo "* TESTCASE list-key aes FAIL Failed to list aes public keys CK_BYTE attribute" + status=1 +fi +# URI +if [[ $(grep -A 69 'p11sak-aes-128' $P11SAK_AES_LONG | grep -c 'URI: pkcs11:.*type=secret-key') == "3" ]]; then + echo "* TESTCASE list-key aes PASS list aes key pkcs#11 URI" +else + echo "* TESTCASE list-key aes FAIL list aes key pkcs#11 URI" + status=1 +fi + +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_AES_XTS_KEY_GEN) && -z $( pkcsconf -t -c $SLOT | grep "Model: EP11") ]]; then + # check AES-XTS 128 + grep -q 'p11sak-aes-xts-128' $P11SAK_AES_XTS_PRE + rc=$? + if [ $rc = 0 ]; then + echo "* TESTCASE generate-key aes-xts-128 PASS Generated random AES-XTS 128 key" + else + echo "* TESTCASE generate-key aes-xts-128 FAIL Failed to generate AES-XTS 128 key" + status=1 + fi + grep -v -q 'p11sak-aes-xts-128' $P11SAK_AES_XTS_POST + rc=$? + if [ $rc = 0 ]; then + echo "* TESTCASE remove-key aes-xts-128 PASS Deleted generated AES-XTS 128 key" + else + echo "* TESTCASE remove-key aes-xts-128 FAIL Failed to delete generated AES-XTS 128 key" + status=1 + fi + + # check AES-XTS 256 + grep -q 'p11sak-aes-xts-256' $P11SAK_AES_XTS_PRE + rc=$? + if [ $rc = 0 ]; then + echo "* TESTCASE generate-key aes-xts-256 PASS Generated random AES-XTS 256 key" + else + echo "* TESTCASE generate-key aes-xts-256 FAIL Failed to generate AES-XTS 256 key" + status=1 + fi + grep -v -q 'p11sak-aes-xts-256' $P11SAK_AES_XTS_POST + rc=$? + if [ $rc = 0 ]; then + echo "* TESTCASE remove-key aes-xts-256 PASS Deleted generated AES-XTS 256 key" + else + echo "* TESTCASE remove-key aes-xts-256 FAIL Failed to delete generated AES-XTS 256 key" + status=1 + fi + + # CK_BBOOL + if [[ $(grep -A 69 'p11sak-aes-xts-128' $P11SAK_AES_XTS_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "2" ]]; then + echo "* TESTCASE list-key aes-xts PASS Listed random aes-xts public keys CK_BBOOL attribute" + else + echo "* TESTCASE list-key aes-xts FAIL Failed to list aes-xts public keys CK_BBOOL attribute" + status=1 + fi + # CK_ULONG + if [[ $(grep -A 69 'p11sak-aes-xts-128' $P11SAK_AES_XTS_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then + echo "* TESTCASE list-key aes-xts PASS Listed random aes-xts public keys CK_ULONG attribute" + else + echo "* TESTCASE list-key aes-xts FAIL Failed to list aes-xts public keys CK_ULONG attribute" + status=1 + fi + # CK_BYTE + if [[ $(grep -A 69 'p11sak-aes-xts-128' $P11SAK_AES_XTS_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then + echo "* TESTCASE list-key aes-xts PASS Listed random aes-xts public keys CK_BYTE attribute" + else + echo "* TESTCASE list-key aes-xts FAIL Failed to list aes-xts public keys CK_BYTE attribute" + status=1 + fi + # URI + if [[ $(grep -A 69 'p11sak-aes-xts-128' $P11SAK_AES_XTS_LONG | grep -c 'URI: pkcs11:.*type=secret-key') == "2" ]]; then + echo "* TESTCASE list-key aes-xts PASS list aes-xts key pkcs#11 URI" + else + echo "* TESTCASE list-key aes-xts FAIL list aes-xts key pkcs#11 URI" + status=1 + fi +else + echo "* TESTCASE generate-key aes-xst-128 SKIP Generated random AES-XTS 128 key" + echo "* TESTCASE remove-key aes-xts-128 SKIP Deleted generated AES-XTS 128 key" + echo "* TESTCASE generate-key aes-xst-256 SKIP Generated random AES-XTS 256 key" + echo "* TESTCASE remove-key aes-xts-256 SKIP Deleted generated AES-XTS 256 key" + echo "* TESTCASE list-key aes-xts SKIP Listed random aes-xts public keys CK_BBOOL attribute" + echo "* TESTCASE list-key aes-xts SKIP Listed random aes-xts public keys CK_ULONG attribute" + echo "* TESTCASE list-key aes-xts SKIP Listed random aes-xts public keys CK_BYTE attribute" + echo "* TESTCASE list-key aes-xts SKIP list aes-xts key pkcs#11 URI" fi - # check RSA 1024 public key grep -q 'p11sak-rsa-1024:pub' $P11SAK_RSA_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key rsa 1024 PASS Generated random rsa 1024 public key" + echo "* TESTCASE generate-key rsa 1024 PASS Generated random rsa 1024 public key" else -echo "* TESTCASE generate-key rsa 1024 FAIL Failed to generate rsa 1024 public key" + echo "* TESTCASE generate-key rsa 1024 FAIL Failed to generate rsa 1024 public key" + status=1 fi grep -v -q 'p11sak-rsa-1024:pub' $P11SAK_RSA_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 1024 public key" + echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 1024 public key" else -echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 1024 public key" + echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 1024 public key" + status=1 fi @@ -296,16 +484,18 @@ grep -q 'p11sak-rsa-2048:pub' $P11SAK_RSA_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key rsa 2048 PASS Generated random rsa 2048 public key" + echo "* TESTCASE generate-key rsa 2048 PASS Generated random rsa 2048 public key" else -echo "* TESTCASE generate-key rsa 2048 FAIL Failed to generate rsa 2048 public key" + echo "* TESTCASE generate-key rsa 2048 FAIL Failed to generate rsa 2048 public key" + status=1 fi grep -v -q 'p11sak-rsa-2048:pub' $P11SAK_RSA_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 2048 public key" + echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 2048 public key" else -echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 2048 public key" + echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 2048 public key" + status=1 fi @@ -313,16 +503,18 @@ grep -q 'p11sak-rsa-4096:pub' $P11SAK_RSA_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key rsa 4096 PASS Generated random rsa 4096 public key" + echo "* TESTCASE generate-key rsa 4096 PASS Generated random rsa 4096 public key" else -echo "* TESTCASE generate-key rsa 4096 FAIL Failed to generate rsa 4096 public key" + echo "* TESTCASE generate-key rsa 4096 FAIL Failed to generate rsa 4096 public key" + status=1 fi grep -v -q 'p11sak-rsa-4096:pub' $P11SAK_RSA_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 4096 public key" + echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 4096 public key" else -echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 4096 public key" + echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 4096 public key" + status=1 fi @@ -330,16 +522,18 @@ grep -q 'p11sak-rsa-1024:prv' $P11SAK_RSA_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key rsa 1024 PASS Generated random rsa 1024 private key" + echo "* TESTCASE generate-key rsa 1024 PASS Generated random rsa 1024 private key" else -echo "* TESTCASE generate-key rsa 1024 FAIL Failed to generate rsa 1024 private key" + echo "* TESTCASE generate-key rsa 1024 FAIL Failed to generate rsa 1024 private key" + status=1 fi grep -v -q 'p11sak-rsa-1024:prv' $P11SAK_RSA_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 1024 private key" + echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 1024 private key" else -echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 1024 private key" + echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 1024 private key" + status=1 fi @@ -347,16 +541,18 @@ grep -q 'p11sak-rsa-2048:prv' $P11SAK_RSA_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key rsa 2048 PASS Generated random rsa 2048 private key" + echo "* TESTCASE generate-key rsa 2048 PASS Generated random rsa 2048 private key" else -echo "* TESTCASE generate-key rsa 2048 FAIL Failed to generate rsa 2048 private key" + echo "* TESTCASE generate-key rsa 2048 FAIL Failed to generate rsa 2048 private key" + status=1 fi grep -v -q 'p11sak-rsa-2048:prv' $P11SAK_RSA_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 2048 private key" + echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 2048 private key" else -echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 2048 private key" + echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 2048 private key" + status=1 fi @@ -364,36 +560,48 @@ grep -q 'p11sak-rsa-4096:prv' $P11SAK_RSA_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key rsa 4096 PASS Generated random rsa 4096 private key" + echo "* TESTCASE generate-key rsa 4096 PASS Generated random rsa 4096 private key" else -echo "* TESTCASE generate-key rsa 4096 FAIL Failed to generate rsa 4096 private key" + echo "* TESTCASE generate-key rsa 4096 FAIL Failed to generate rsa 4096 private key" + status=1 fi grep -v -q 'p11sak-rsa-4096:prv' $P11SAK_RSA_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 4096 private key" + echo "* TESTCASE remove-key rsa PASS Deleted generated rsa 4096 private key" else -echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 4096 private key" + echo "* TESTCASE remove-key rsa FAIL Failed to delete generated rsa 4096 private key" + status=1 fi # CK_BBOOL -if [[ $(grep -A 205 'p11sak-rsa-1024:pub' $P11SAK_RSA_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "6" ]]; then -echo "* TESTCASE list-key rsa PASS Listed random rsa public keys CK_BBOOL attribute" +if [[ $(grep -A 211 'p11sak-rsa-1024:pub' $P11SAK_RSA_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "6" ]]; then + echo "* TESTCASE list-key rsa PASS Listed random rsa public keys CK_BBOOL attribute" else -echo "* TESTCASE list-key rsa FAIL Failed to list rsa public keys CK_BBOOL attribute" + echo "* TESTCASE list-key rsa FAIL Failed to list rsa public keys CK_BBOOL attribute" + status=1 fi # CK_ULONG -if [[ $(grep -A 205 'p11sak-rsa-1024:pub' $P11SAK_RSA_LONG | grep -c 'CKA_MODULUS_BITS:') == "3" ]]; then -echo "* TESTCASE list-key rsa PASS Listed random rsa public keys CK_ULONG attribute" +if [[ $(grep -A 211 'p11sak-rsa-1024:pub' $P11SAK_RSA_LONG | grep -c 'CKA_MODULUS_BITS:') == "3" ]]; then + echo "* TESTCASE list-key rsa PASS Listed random rsa public keys CK_ULONG attribute" else -echo "* TESTCASE list-key rsa FAIL Failed to list rsa public keys CK_ULONG attribute" + echo "* TESTCASE list-key rsa FAIL Failed to list rsa public keys CK_ULONG attribute" + status=1 fi # CK_BYTE -if [[ $(grep -A 205 'p11sak-rsa-1024:pub' $P11SAK_RSA_LONG | grep -c 'CKA_MODULUS:') == "6" ]]; then -echo "* TESTCASE list-key rsa PASS Listed random rsa public keys CK_BYTE attribute" +if [[ $(grep -A 211 'p11sak-rsa-1024:pub' $P11SAK_RSA_LONG | grep -c 'CKA_MODULUS:') == "6" ]]; then + echo "* TESTCASE list-key rsa PASS Listed random rsa public keys CK_BYTE attribute" else -echo "* TESTCASE list-key rsa FAIL Failed to list rsa public keys CK_BYTE attribute" + echo "* TESTCASE list-key rsa FAIL Failed to list rsa public keys CK_BYTE attribute" + status=1 +fi +# URI +if [[ $(grep -A 211 'p11sak-rsa-1024:pub' $P11SAK_RSA_LONG | grep -c 'URI: pkcs11:.*type=public') == "3" ]]; then + echo "* TESTCASE list-key rsa PASS list rsa public key pkcs#11 URI" +else + echo "* TESTCASE list-key rsa FAIL list rsa public key pkcs#11 URI" + status=1 fi @@ -401,16 +609,18 @@ grep -q 'p11sak-ec-prime256v1:pub' $P11SAK_EC_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key ec prime256v1 PASS Generated random ec prime256v1 public key" + echo "* TESTCASE generate-key ec prime256v1 PASS Generated random ec prime256v1 public key" else -echo "* TESTCASE generate-key ec prime256v1 FAIL Failed to generate ec prime256v1 public key" + echo "* TESTCASE generate-key ec prime256v1 FAIL Failed to generate ec prime256v1 public key" + status=1 fi grep -v -q 'p11sak-ec-prime256v1:pub' $P11SAK_EC_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key ec prime256v1 PASS Deleted generated ec prime256v1 public key" + echo "* TESTCASE remove-key ec prime256v1 PASS Deleted generated ec prime256v1 public key" else -echo "* TESTCASE remove-key ec prime256v1 FAIL Failed to delete generated ec prime256v1 public key" + echo "* TESTCASE remove-key ec prime256v1 FAIL Failed to delete generated ec prime256v1 public key" + status=1 fi @@ -418,16 +628,18 @@ grep -q 'p11sak-ec-secp384r1:pub' $P11SAK_EC_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key ec secp384r1 PASS Generated random ec secp384r1 public key" + echo "* TESTCASE generate-key ec secp384r1 PASS Generated random ec secp384r1 public key" else -echo "* TESTCASE generate-key ec secp384r1 FAIL Failed to generate ec secp384r1 public key" + echo "* TESTCASE generate-key ec secp384r1 FAIL Failed to generate ec secp384r1 public key" + status=1 fi grep -v -q 'p11sak-ec-secp384r1:pub' $P11SAK_EC_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key ec secp384r1 PASS Deleted generated ec secp384r1 public key" + echo "* TESTCASE remove-key ec secp384r1 PASS Deleted generated ec secp384r1 public key" else -echo "* TESTCASE remove-key ec secp384r1 FAIL Failed to delete generated ec secp384r1 public key" + echo "* TESTCASE remove-key ec secp384r1 FAIL Failed to delete generated ec secp384r1 public key" + status=1 fi @@ -435,16 +647,18 @@ grep -q 'p11sak-ec-secp521r1:pub' $P11SAK_EC_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key ec secp521r1 PASS Generated random ec secp521r1 public key" + echo "* TESTCASE generate-key ec secp521r1 PASS Generated random ec secp521r1 public key" else -echo "* TESTCASE generate-key ec secp521r1 FAIL Failed to generate ec secp521r1 public key" + echo "* TESTCASE generate-key ec secp521r1 FAIL Failed to generate ec secp521r1 public key" + status=1 fi grep -v -q 'p11sak-ec-secp521r1:pub' $P11SAK_EC_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key ec secp521r1 PASS Deleted generated ec secp521r1 public key" + echo "* TESTCASE remove-key ec secp521r1 PASS Deleted generated ec secp521r1 public key" else -echo "* TESTCASE remove-key ec secp521r1 FAIL Failed to delete generated ec secp521r1 public key" + echo "* TESTCASE remove-key ec secp521r1 FAIL Failed to delete generated ec secp521r1 public key" + status=1 fi @@ -452,16 +666,18 @@ grep -q 'p11sak-ec-prime256v1:prv' $P11SAK_EC_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key ec prime256v1 PASS Generated random ec prime256v1 private key" + echo "* TESTCASE generate-key ec prime256v1 PASS Generated random ec prime256v1 private key" else -echo "* TESTCASE generate-key ec prime256v1 FAIL Failed to generate ec prime256v1 private key" + echo "* TESTCASE generate-key ec prime256v1 FAIL Failed to generate ec prime256v1 private key" + status=1 fi grep -v -q 'p11sak-ec-prime256v1:prv' $P11SAK_EC_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key ec prime256v1 PASS Deleted generated ec prime256v1 private key" + echo "* TESTCASE remove-key ec prime256v1 PASS Deleted generated ec prime256v1 private key" else -echo "* TESTCASE remove-key ec prime256v1 FAIL Failed to delete generated ec prime256v1 private key" + echo "* TESTCASE remove-key ec prime256v1 FAIL Failed to delete generated ec prime256v1 private key" + status=1 fi @@ -469,16 +685,18 @@ grep -q 'p11sak-ec-secp384r1:prv' $P11SAK_EC_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key ec secp384r1 PASS Generated random ec secp384r1 private key" + echo "* TESTCASE generate-key ec secp384r1 PASS Generated random ec secp384r1 private key" else -echo "* TESTCASE generate-key ec secp384r1 FAIL Failed to generate ec secp384r1 private key" + echo "* TESTCASE generate-key ec secp384r1 FAIL Failed to generate ec secp384r1 private key" + status=1 fi grep -v -q 'p11sak-ec-secp384r1:prv' $P11SAK_EC_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key ec secp384r1 PASS Deleted generated ec secp384r1 private key" + echo "* TESTCASE remove-key ec secp384r1 PASS Deleted generated ec secp384r1 private key" else -echo "* TESTCASE remove-key ec secp384r1 FAIL Failed to delete generated ec secp384r1 private key" + echo "* TESTCASE remove-key ec secp384r1 FAIL Failed to delete generated ec secp384r1 private key" + status=1 fi @@ -486,36 +704,136 @@ grep -q 'p11sak-ec-secp521r1:prv' $P11SAK_EC_PRE rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE generate-key ec secp521r1 PASS Generated random ec secp521r1 private key" + echo "* TESTCASE generate-key ec secp521r1 PASS Generated random ec secp521r1 private key" else -echo "* TESTCASE generate-key ec secp521r1 FAIL Failed to generate ec secp521r1 private key" + echo "* TESTCASE generate-key ec secp521r1 FAIL Failed to generate ec secp521r1 private key" + status=1 fi grep -v -q 'p11sak-ec-secp521r1:prv' $P11SAK_EC_POST rc=$? if [ $rc = 0 ]; then -echo "* TESTCASE remove-key ec secp521r1 PASS Deleted generated ec secp521r1 private key" + echo "* TESTCASE remove-key ec secp521r1 PASS Deleted generated ec secp521r1 private key" else -echo "* TESTCASE remove-key ec secp521r1 FAIL Failed to delete generated ec secp521r1 private key" + echo "* TESTCASE remove-key ec secp521r1 FAIL Failed to delete generated ec secp521r1 private key" + status=1 fi # CK_BBOOL -if [[ $(grep -A 84 'p11sak-ec-prime256v1:pub' $P11SAK_EC_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "6" ]]; then -echo "* TESTCASE list-key ec PASS Listed random ec public keys CK_BBOOL attribute" +if [[ $(grep -A 99 'p11sak-ec-prime256v1:pub' $P11SAK_EC_LONG | grep -c 'CKA_IBM_PROTKEY_EXTRACTABLE: CK_FALSE') == "6" ]]; then + echo "* TESTCASE list-key ec PASS Listed random ec public keys CK_BBOOL attribute" else -echo "* TESTCASE list-key ec FAIL Failed to list ec public keys CK_BBOOL attribute" + echo "* TESTCASE list-key ec FAIL Failed to list ec public keys CK_BBOOL attribute" + status=1 fi # CK_ULONG -if [[ $(grep -A 84 'p11sak-ec-prime256v1:pub' $P11SAK_EC_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then -echo "* TESTCASE list-key ec PASS Listed random ec public keys CK_ULONG attribute" +if [[ $(grep -A 99 'p11sak-ec-prime256v1:pub' $P11SAK_EC_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then + echo "* TESTCASE list-key ec PASS Listed random ec public keys CK_ULONG attribute" else -echo "* TESTCASE list-key ec FAIL Failed to list ec public keys CK_ULONG attribute" + echo "* TESTCASE list-key ec FAIL Failed to list ec public keys CK_ULONG attribute" + status=1 fi # CK_BYTE -if [[ $(grep -A 84 'p11sak-ec-prime256v1:pub' $P11SAK_EC_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then -echo "* TESTCASE list-key ec PASS Listed random ec public keys CK_BYTE attribute" +if [[ $(grep -A 99 'p11sak-ec-prime256v1:pub' $P11SAK_EC_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then + echo "* TESTCASE list-key ec PASS Listed random ec public keys CK_BYTE attribute" +else + echo "* TESTCASE list-key ec FAIL Failed to list ec public keys CK_BYTE attribute" + status=1 +fi +# URI +if [[ $(grep -A 99 'p11sak-ec-prime256v1:pub' $P11SAK_EC_LONG | grep -c 'URI: pkcs11:.*type=public') == "3" ]]; then + echo "* TESTCASE list-key ec PASS list ec public key pkcs#11 URI" +else + echo "* TESTCASE list-key ec FAIL list ec public key pkcs#11 URI" + status=1 +fi + + +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_IBM_DILITHIUM) ]]; then + # CK_BBOOL + if [[ $(grep -A 35 'p11sak-ibm-dilithium' $P11SAK_IBM_DIL_LONG | grep -c 'CK_TRUE') == "12" ]]; then + echo "* TESTCASE list-key ibm-dilithium PASS Listed random ibm-dilithium public keys CK_BBOOL attribute" + else + echo "* TESTCASE list-key ibm-dilithium FAIL Failed to list ibm-dilithium public keys CK_BBOOL attribute" + status=1 + fi + # CK_ULONG + if [[ $(grep -A 35 'p11sak-ibm-dilithium' $P11SAK_IBM_DIL_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then + echo "* TESTCASE list-key ibm-dilithium PASS Listed random ibm-dilithium public keys CK_ULONG attribute" + else + echo "* TESTCASE list-key ibm-dilithium FAIL Failed to list ibm-dilithium public keys CK_ULONG attribute" + status=1 + fi + # CK_BYTE + if [[ $(grep -A 35 'p11sak-ibm-dilithium' $P11SAK_IBM_DIL_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then + echo "* TESTCASE list-key ibm-dilithium PASS Listed random ibm-dilithium public keys CK_BYTE attribute" + else + echo "* TESTCASE list-key ibm-dilithium FAIL Failed to list ibm-dilithium public keys CK_BYTE attribute" + status=1 + fi +else + echo "* TESTCASE list-key ibm-dilithium SKIP Listed random ibm-dilithium public keys CK_BBOOL attribute" + echo "* TESTCASE list-key ibm-dilithium SKIP Listed random ibm-dilithium public keys CK_ULONG attribute" + echo "* TESTCASE list-key ibm-dilithium SKIP Listed random ibm-dilithium public keys CK_BYTE attribute" +fi + +if [[ -n $( pkcsconf -m -c $SLOT | grep CKM_IBM_KYBER) ]]; then + # CK_BBOOL + if [[ $(grep -A 35 'p11sak-ibm-kyber' $P11SAK_IBM_KYBER_LONG | grep -c 'CK_TRUE') == "12" ]]; then + echo "* TESTCASE list-key ibm-kyber PASS Listed random ibm-kyber public keys CK_BBOOL attribute" + else + echo "* TESTCASE list-key ibm-kyber FAIL Failed to list ibm-kyber public keys CK_BBOOL attribute" + status=1 + fi + # CK_ULONG + if [[ $(grep -A 35 'p11sak-ibm-kyber' $P11SAK_IBM_KYBER_LONG | grep -c 'CKA_MODULUS_BITS:') == "0" ]]; then + echo "* TESTCASE list-key ibm-kyber PASS Listed random ibm-kyber public keys CK_ULONG attribute" + else + echo "* TESTCASE list-key ibm-kyber FAIL Failed to list ibm-kyber public keys CK_ULONG attribute" + status=1 + fi + # CK_BYTE + if [[ $(grep -A 35 'p11sak-ibm-kyber' $P11SAK_IBM_KYBER_LONG | grep -c 'CKA_MODULUS:') == "0" ]]; then + echo "* TESTCASE list-key ibm-kyber PASS Listed random ibm-kyber public keys CK_BYTE attribute" + else + echo "* TESTCASE list-key ibm-kyber FAIL Failed to list ibm-kyber public keys CK_BYTE attribute" + status=1 + fi +else + echo "* TESTCASE list-key ibm-kyber SKIP Listed random ibm-kyber public keys CK_BBOOL attribute" + echo "* TESTCASE list-key ibm-kyber SKIP Listed random ibm-kyber public keys CK_ULONG attribute" + echo "* TESTCASE list-key ibm-kyber SKIP Listed random ibm-kyber public keys CK_BYTE attribute" +fi + +# check token pin handling +if [ $RC_P11SAK_PINOPT = 0 ]; then + echo "* TESTCASE list-key pin-opt PASS Token pin handling (opt)" +else + echo "* TESTCASE list-key pin-option FAIL Token pin handling (opt)" +fi + +if [ $RC_P11SAK_PINENV = 0 ]; then + echo "* TESTCASE list-key pin-env PASS Token pin handling (env)" +else + echo "* TESTCASE list-key pin-env FAIL Token pin handling (env)" +fi + +if [ $RC_P11SAK_PINCON = 0 ]; then + echo "* TESTCASE list-key pin-prompt PASS Token pin handling (prompt)" +else + echo "* TESTCASE list-key pin-prompt FAIL Token pin handling (prompt)" +fi + +if diff -q $P11SAK_ALL_PINOPT $P11SAK_ALL_PINENV ; then + echo "* TESTCASE list-key pin-opt-env PASS Token pin opt/env output compare" +else + echo "* TESTCASE list-key pin-opt-env FAIL Token pin opt/env output compare" +fi + +if diff -q $P11SAK_ALL_PINOPT $P11SAK_ALL_PINCON ; then + echo "* TESTCASE list-key pin-opt-prompt PASS Token pin opt/prompt output compare" else -echo "* TESTCASE list-key ec FAIL Failed to list ec public keys CK_BYTE attribute" + echo "* TESTCASE list-key pin-opt-prompt FAIL Token pin opt/prompt output compare" fi @@ -531,12 +849,25 @@ rm -f $P11SAK_AES_PRE rm -f $P11SAK_AES_LONG rm -f $P11SAK_AES_POST +rm -f $P11SAK_AES_XTS_PRE +rm -f $P11SAK_AES_XTS_LONG +rm -f $P11SAK_AES_XTS_POST rm -f $P11SAK_RSA_PRE rm -f $P11SAK_RSA_LONG rm -f $P11SAK_RSA_POST rm -f $P11SAK_EC_PRE rm -f $P11SAK_EC_LONG rm -f $P11SAK_EC_POST +rm -f $P11SAK_IBM_DIL_PRE +rm -f $P11SAK_IBM_DIL_LONG +rm -f $P11SAK_IBM_DIL_POST +rm -f $P11SAK_IBM_KYBER_PRE +rm -f $P11SAK_IBM_KYBER_LONG +rm -f $P11SAK_IBM_KYBER_POST +rm -f $P11SAK_ALL_PINOPT +rm -f $P11SAK_ALL_PINENV +rm -f $P11SAK_ALL_PINCON -echo "** Now DONE testing - 'p11sak_test.sh'" +echo "** Now DONE testing - 'p11sak_test.sh' - rc = $status" +exit $status diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/pkcsconf_test.sh opencryptoki-3.20.0+dfsg/testcases/misc_tests/pkcsconf_test.sh --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/pkcsconf_test.sh 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/pkcsconf_test.sh 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,130 @@ +#!/bin/bash +# +# COPYRIGHT (c) International Business Machines Corp. 2022 +# +# This program is provided under the terms of the Common Public License, +# version 1.0 (CPL-1.0). Any use, reproduction or distribution for this software +# constitutes recipient's acceptance of CPL-1.0 terms which can be found +# in the file LICENSE file or at https://opensource.org/licenses/cpl1.0.php + +# functions +print_test_result() { + local rc=$1 + local name=$2 + local subn=$3 + local mesg=$4 + + if [ ${rc} = 0 ]; then + echo "* TESTCASE ${name} ${subn} PASS ${mesg}" + else + echo "* TESTCASE ${name} ${subn} FAIL ${mesg}" + fi +} + +echo "** Now executing 'pkcsconf_test.sh'" + +# create temporary directory +TMP=$(mktemp -d) + +# define output files +PKCSCONF_INFO=${TMP}/pkcsconf-info.out +PKCSCONF_SLOT=${TMP}/pkcsconf-slot.out +PKCSCONF_TOKEN=${TMP}/pkcsconf-token.out + +# list info/slots/tokens +pkcsconf -i &> $PKCSCONF_INFO +pkcsconf -s &> $PKCSCONF_SLOT +pkcsconf -t &> $PKCSCONF_TOKEN + +# extract information elements +INFO_LIBVERS=$(cat ${PKCSCONF_INFO} | grep -Po 'Library Version:\s+\K[0-9]+.[0-9]+') +INFO_LIBMANU=$(cat ${PKCSCONF_INFO} | grep -Po 'Manufacturer:\s+\K\S*') +INFO_LIBDESC=$(cat ${PKCSCONF_INFO} | grep -Po 'Library Description:\s+\K\S*') + +# extract information URI elements +URI_INFO_LIBVERS=$(cat ${PKCSCONF_INFO} | grep -Po 'URI:\s*pkcs11:.*library-version=\K[^;]*') +URI_INFO_LIBMANU=$(cat ${PKCSCONF_INFO} | grep -Po 'URI:\s*pkcs11:.*library-manufacturer=\K[^;]*') +URI_INFO_LIBDESC=$(cat ${PKCSCONF_INFO} | grep -Po 'URI:\s*pkcs11:.*library-description=\K[^;]*') + +# extract slot elements (only first slot) +SLOT_ID=$( cat ${PKCSCONF_SLOT} | grep -Po '^Slot #\K[0-9]+' | head -n1) +SLOT_MANU=$(cat ${PKCSCONF_SLOT} | grep -Po 'Manufacturer:\s+\K\S*' | head -n1) +SLOT_DESC=$(cat ${PKCSCONF_SLOT} | grep -Po 'Description:\s+\K\S*' | head -n1) + +# extract slot URI elements (only first slot) +URI_SLOT_ID=$( cat ${PKCSCONF_SLOT} | grep -Po 'URI:\s*pkcs11:.*slot-id=\K[^;]*' | head -n1) +URI_SLOT_MANU=$(cat ${PKCSCONF_SLOT} | grep -Po 'URI:\s*pkcs11:.*slot-manufacturer=\K[^;]*' | head -n1) +URI_SLOT_DESC=$(cat ${PKCSCONF_SLOT} | grep -Po 'URI:\s*pkcs11:.*slot-description=\K[^;]*' | head -n1) + +# extract token elements (only first token) +TOKEN_LABL=$(cat ${PKCSCONF_TOKEN} | grep -Po 'Label:\s+\K\S*' | head -n1) +TOKEN_MANU=$(cat ${PKCSCONF_TOKEN} | grep -Po 'Manufacturer:\s+\K\S*' | head -n1) +TOKEN_MODL=$(cat ${PKCSCONF_TOKEN} | grep -Po 'Model:\s+\K\S*' | head -n1) + +# extract token URI elements (only first token) +URI_TOKEN_LABL=$(cat ${PKCSCONF_TOKEN} | grep -Po 'URI:\s*pkcs11:.*token=\K[^;]*' | head -n1) +URI_TOKEN_MANU=$(cat ${PKCSCONF_TOKEN} | grep -Po 'URI:\s*pkcs11:.*manufacturer=\K[^;]*' | head -n1) +URI_TOKEN_MODL=$(cat ${PKCSCONF_TOKEN} | grep -Po 'URI:\s*pkcs11:.*model=\K[^;]*' | head -n1) + +# information test cases +test -n "${INFO_LIBVERS}" -o \ + -n "${INFO_LIBMANU}" -o \ + -n "${INFO_LIBDESC}" +print_test_result $? "pkcsconf" "info" "check output for all required library fields" + +test -n "${URI_INFO_LIBVERS}" -o \ + -n "${URI_INFO_LIBMANU}" -o \ + -n "${URI_INFO_LIBDESC}" +print_test_result $? "pkcsconf" "info" "check URI for all required library fields" + +test "${INFO_LIBVERS}" = "${URI_INFO_LIBVERS}" +print_test_result $? "pkcsconf" "info" "check library version in URI" + +test "${INFO_LIBMANU}" = "${URI_INFO_LIBMANU}" +print_test_result $? "pkcsconf" "info" "check library manufacturer in URI" + +test "${INFO_LIBDESC}" = "${URI_INFO_LIBDESC}" +print_test_result $? "pkcsconf" "info" "check library description in URI" + +# slot test cases +test -n "${SLOT_ID}" -o \ + -n "${SLOT_MANU}" -o \ + -n "${SLOT_DESC}" +print_test_result $? "pkcsconf" "slot" "check output for all required slot fields" + +test -n "${URI_SLOT_ID}" -o \ + -n "${URI_SLOT_MANU}" -o \ + -n "${URI_SLOT_DESC}" +print_test_result $? "pkcsconf" "slot" "check URI for all required slot fields" + +test "${SLOT_ID}" = "${URI_SLOT_ID}" +print_test_result $? "pkcsconf" "slot" "check slot id in URI" + +test "${SLOT_MANU}" = "${URI_SLOT_MANU}" +print_test_result $? "pkcsconf" "slot" "check slot manufacturer in URI" + +test "${SLOT_DESC}" = "${URI_SLOT_DESC}" +print_test_result $? "pkcsconf" "slot" "check slot description in URI" + +# token test cases +test -n "${TOKEN_LABL}" -o \ + -n "${TOKEN_MANU}" -o \ + -n "${TOKEN_MODL}" +print_test_result $? "pkcsconf" "token" "check output for all required token fields" + +test -n "${URI_TOKEN_LABL}" -o \ + -n "${URI_TOKEN_MANU}" -o \ + -n "${URI_TOKEN_MODL}" +print_test_result $? "pkcsconf" "token" "check URI for all required token fields" + +test "${TOKEN_LABL}" = "${URI_TOKEN_LABL}" +print_test_result $? "pkcsconf" "token" "check token label in URI" + +test "${TOKEN_MANU}" = "${URI_TOKEN_MANU}" +print_test_result $? "pkcsconf" "token" "check token manufacturer in URI" + +test "${TOKEN_MODL}" = "${URI_TOKEN_MODL}" +print_test_result $? "pkcsconf" "token" "check token model in URI" + +# remove tmp +rm -rf ${TMP} &> /dev/null diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/reencrypt.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/reencrypt.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/reencrypt.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/reencrypt.c 2023-02-13 09:22:42.000000000 +0100 @@ -361,7 +361,7 @@ if (!keysize_supported(slot_id, mech2->key_gen_mech.mechanism, mech2->rsa_modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", slot_id, mech2->rsa_modbits); goto testcase_cleanup; } @@ -609,8 +609,8 @@ if (!keysize_supported(slot_id, mech1->key_gen_mech.mechanism, mech1->rsa_modbits)) { - testsuite_skip(NUM_REENCRYPT_TESTS, "Token in slot %ld cannot be " - "used with modbits.='%ld'", slot_id, + testsuite_skip(NUM_REENCRYPT_TESTS, "Token in slot %lu cannot be " + "used with modbits='%lu'", slot_id, mech1->rsa_modbits); goto testcase_cleanup; } @@ -758,7 +758,7 @@ return rc; } -CK_RV do_reencrypt_tests() +CK_RV do_reencrypt_tests(void) { CK_ULONG i; CK_RV rc; diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/speed.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/speed.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/speed.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/speed.c 2023-02-13 09:22:42.000000000 +0100 @@ -92,8 +92,8 @@ {CKA_PUBLIC_EXPONENT, &pub_exp, sizeof(pub_exp)} }; - testcase_begin("RSA PKCS Encrypt with keylen=%d datalen=%d", - keylength, (int) sizeof(data1)); + testcase_begin("RSA PKCS Encrypt with keylen=%d datalen=%lu", + keylength, sizeof(data1)); if (!mech_supported(SLOT_ID, CKM_RSA_PKCS_KEY_PAIR_GEN)) { testcase_skip("Slot %lu doesn't support CKM_RSA_PKCS_KEY_PAIR_GEN (0x%x)", @@ -174,15 +174,15 @@ max_time /= 1000; avg_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldms max=%ldms avg=%ldms " + printf("%lu iterations: total=%lums min=%lums max=%lums avg=%lums " "op/s=%.3f\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time); - testcase_pass("RSA PKCS Encrypt with keylen=%d datalen=%d", - keylength, (int) sizeof(data1)); + testcase_pass("RSA PKCS Encrypt with keylen=%d datalen=%lu", + keylength, sizeof(data1)); - testcase_begin("RSA PKCS Decrypt with keylen=%d datalen=%d", - keylength, (int) encdata_len); + testcase_begin("RSA PKCS Decrypt with keylen=%d datalen=%lu", + keylength, encdata_len); testcase_new_assertion(); tot_time = 0; @@ -235,12 +235,12 @@ max_time /= 1000; avg_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldms max=%ldms avg=%ldms " + printf("%lu iterations: total=%lums min=%lums max=%lums avg=%lums " "op/s=%.3f\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time); - testcase_pass("RSA PKCS Decrypt with keylen=%d datalen=%d", - keylength, (int) encdata_len); + testcase_pass("RSA PKCS Decrypt with keylen=%d datalen=%lu", + keylength, encdata_len); testcase_cleanup: testcase_closeall_session(); @@ -327,7 +327,7 @@ max_time /= 1000; avg_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldms max=%ldms avg=%ldms " + printf("%lu iterations: total=%lums min=%lums max=%lums avg=%lums " "op/s=%.3f\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time); @@ -367,8 +367,8 @@ {CKA_PUBLIC_EXPONENT, &pub_exp, sizeof(pub_exp)} }; - testcase_begin("RSA PKCS Sign with keylen=%d datalen=%d", - keylength, (int) sizeof(data1)); + testcase_begin("RSA PKCS Sign with keylen=%d datalen=%lu", + keylength, sizeof(data1)); if (!mech_supported(SLOT_ID, CKM_RSA_PKCS_KEY_PAIR_GEN)) { testcase_skip("Slot %lu doesn't support CKM_RSA_PKCS_KEY_PAIR_GEN (0x%x)", @@ -446,15 +446,15 @@ max_time /= 1000; avg_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldms max=%ldms avg=%ldms " + printf("%lu iterations: total=%lums min=%lums max=%lums avg=%lums " "op/s=%.3f\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time); - testcase_pass("RSA PKCS Sign with keylen=%d datalen=%d", - keylength, (int) sizeof(data1)); + testcase_pass("RSA PKCS Sign with keylen=%d datalen=%lu", + keylength, sizeof(data1)); - testcase_begin("RSA PKCS Verify with keylen=%d datalen=%d", - keylength, (int) sizeof(data1)); + testcase_begin("RSA PKCS Verify with keylen=%d datalen=%lu", + keylength, sizeof(data1)); testcase_new_assertion(); tot_time = 0; @@ -494,12 +494,12 @@ max_time /= 1000; avg_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldms max=%ldms avg=%ldms " + printf("%lu iterations: total=%lums min=%lums max=%lums avg=%lums " "op/s=%.3f\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time); - testcase_pass("RSA PKCS Verify with keylen=%d datalen=%d", - keylength, (int) sizeof(data1)); + testcase_pass("RSA PKCS Verify with keylen=%d datalen=%lu", + keylength, sizeof(data1)); testcase_cleanup: testcase_closeall_session(); @@ -626,7 +626,7 @@ // us -> ms tot_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldus max=%ldus avg=%ldus " + printf("%lu iterations: total=%lums min=%luus max=%luus avg=%luus " "op/s=%.3f %.3fMB/s\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time, (((double) (iterations * 1000) / (double) (1024 * 1024)) * @@ -677,7 +677,7 @@ // us -> ms tot_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldus max=%ldus avg=%ldus " + printf("%lu iterations: total=%lums min=%luus max=%luus avg=%luus " "op/s=%.3f %.3fMB/s\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time, (((double) (iterations * 1000) / (double) (1024 * 1024)) * @@ -722,7 +722,7 @@ SYSTEMTIME t1, t2; CK_ULONG avg_time, tot_time, min_time, max_time, diff; - testcase_begin("AES Encrypt with mode=%s keylen=%ld datalen=%d", + testcase_begin("AES Encrypt with mode=%s keylen=%lu datalen=%d", mode, key_len * 8, BIG_REQUEST); if (!mech_supported(SLOT_ID, CKM_AES_KEY_GEN)) { @@ -819,16 +819,16 @@ // us -> ms tot_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldus max=%ldus avg=%ldus " + printf("%lu iterations: total=%lums min=%luus max=%luus avg=%luus " "op/s=%.3f %.3fMB/s\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time, (((double) (iterations * 1000) / (double) (1024 * 1024)) * BIG_REQUEST) / (double) tot_time); - testcase_pass("AES Encrypt with mode=%s keylen=%ld datalen=%d", + testcase_pass("AES Encrypt with mode=%s keylen=%lu datalen=%d", mode, key_len * 8, BIG_REQUEST); - testcase_begin("AES Decrypt with mode=%s keylen=%ld datalen=%d", + testcase_begin("AES Decrypt with mode=%s keylen=%lu datalen=%d", mode, key_len * 8, BIG_REQUEST); testcase_new_assertion(); @@ -869,13 +869,13 @@ // us -> ms tot_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldus max=%ldus avg=%ldus " + printf("%lu iterations: total=%lums min=%luus max=%luus avg=%luus " "op/s=%.3f %.3fMB/s\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time, (((double) (iterations * 1000) / (double) (1024 * 1024)) * BIG_REQUEST) / (double) tot_time); - testcase_pass("AES Decrypt with mode=%s keylen=%ld datalen=%d", + testcase_pass("AES Decrypt with mode=%s keylen=%lu datalen=%d", mode, key_len * 8, BIG_REQUEST); testcase_cleanup: @@ -970,7 +970,7 @@ if (h_len != hash_len) { testcase_error - ("returned hashlen %ld doesn't match to expected len %ld\n", + ("returned hashlen %lu doesn't match to expected len %lu\n", h_len, hash_len); rc = CKR_FUNCTION_FAILED; goto testcase_cleanup; @@ -993,7 +993,7 @@ // us -> ms tot_time /= 1000; - printf("%ld iterations: total=%ldms min=%ldus max=%ldus avg=%ldus " + printf("%lu iterations: total=%lums min=%luus max=%luus avg=%luus " "op/s=%.3f %.3fMB/s\n", iterations, tot_time, min_time, max_time, avg_time, (double) (iterations * 1000) / (double) tot_time, (((double) (iterations * 1000) / (double) (1024 * 1024)) * diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/tok2tok_transport.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/tok2tok_transport.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/tok2tok_transport.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/tok2tok_transport.c 2023-02-13 09:22:42.000000000 +0100 @@ -190,7 +190,20 @@ .wrapping_mech = { CKM_AES_CBC_PAD, aes_iv, sizeof(aes_iv) }, .wrapping_key_gen_mech = { CKM_AES_KEY_GEN, 0, 0 }, .sym_keylen = 32, - }, { + }, + { + .name = "Wrap/Unwrap with AES 128 XTS", + .wrapping_mech = { CKM_AES_XTS, aes_iv, sizeof(aes_iv) }, + .wrapping_key_gen_mech = { CKM_AES_XTS_KEY_GEN, 0, 0 }, + .sym_keylen = 32, + }, + { + .name = "Wrap/Unwrap with AES 256 XTS", + .wrapping_mech = { CKM_AES_XTS, aes_iv, sizeof(aes_iv) }, + .wrapping_key_gen_mech = { CKM_AES_XTS_KEY_GEN, 0, 0 }, + .sym_keylen = 64, + }, + { .name = "Wrap/Unwrap with DES ECB", .wrapping_mech = { CKM_DES_ECB, 0, 0 }, .wrapping_key_gen_mech = { CKM_DES_KEY_GEN, 0, 0 }, @@ -274,6 +287,18 @@ .sym_keylen = 32, }, { + .name = "key type AES-XTS 128", + .wrapped_key_gen_mech = { CKM_AES_XTS_KEY_GEN, 0, 0 }, + .operation_mech = { CKM_AES_XTS, aes_iv, sizeof(aes_iv) }, + .sym_keylen = 32, + }, + { + .name = "key type AES-XTS 256", + .wrapped_key_gen_mech = { CKM_AES_XTS_KEY_GEN, 0, 0 }, + .operation_mech = { CKM_AES_XTS, aes_iv, sizeof(aes_iv) }, + .sym_keylen = 64, + }, + { .name = "key type DES3", .wrapped_key_gen_mech = { CKM_DES3_KEY_GEN, 0, 0 }, .operation_mech = { CKM_DES3_ECB, 0, 0 }, @@ -385,6 +410,7 @@ /* Perform Encrypt/Decrypt operation */ switch (mech->mechanism) { case CKM_AES_ECB: + case CKM_AES_XTS: input_size = 16; encr_key = sym_key1; decr_key = sym_key2; @@ -581,13 +607,13 @@ if (!keysize_supported(slot_id1, tsuite->wrapped_key_gen_mech.mechanism, tsuite->rsa_modbits)) { - testcase_skip("Token in slot %lu cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", slot_id1, tsuite->rsa_modbits); goto testcase_cleanup; } if (!keysize_supported(slot_id2, tsuite->wrapped_key_gen_mech.mechanism, tsuite->rsa_modbits)) { - testcase_skip("Token in slot %lu cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", slot_id2, tsuite->rsa_modbits); goto testcase_cleanup; } @@ -606,7 +632,7 @@ goto testcase_cleanup; } } - if (is_soft_token(slot_id1) || is_cca_token(slot_id2)) { + if (is_soft_token(slot_id1) || is_soft_token(slot_id2)) { if (!is_valid_soft_pubexp(tsuite->rsa_publ_exp, tsuite->rsa_publ_exp_len)) { testcase_skip("Soft Token in scannot be used with publ_exp.='%s'", s); @@ -637,6 +663,13 @@ break; case CKM_AES_KEY_GEN: + case CKM_AES_XTS_KEY_GEN: + if ((is_ep11_token(slot_id1) || is_ep11_token(slot_id2)) && + tsuite->wrapped_key_gen_mech.mechanism == CKM_AES_XTS_KEY_GEN) { + testcase_skip("Skipping as AES XTS is supported only with protected keys"); + rc = CKR_OK; + goto testcase_cleanup; + } rc = generate_AESKey(session1, tsuite->sym_keylen, CK_TRUE, &tsuite->wrapped_key_gen_mech, &sym_key); break; @@ -750,6 +783,7 @@ /* Get class and key type from original key */ switch (tsuite->wrapped_key_gen_mech.mechanism) { case CKM_AES_KEY_GEN: + case CKM_AES_XTS_KEY_GEN: case CKM_GENERIC_SECRET_KEY_GEN: unwrap_tmpl_num = 3; break; @@ -833,7 +867,8 @@ goto testcase_cleanup; } - if (key_type == CKK_AES || key_type == CKK_GENERIC_SECRET) { + if (key_type == CKK_AES || key_type == CKK_AES_XTS || + key_type == CKK_GENERIC_SECRET) { /* Check if the unwrapped key has the desired key length */ rc = funcs->C_GetAttributeValue(session2, unwrapped_key, getattr_tmpl, 1); @@ -902,9 +937,9 @@ char *s = NULL; CK_BYTE modulus[512]; CK_BYTE publ_exp[16]; - CK_BYTE key[32]; + CK_BYTE key[64]; CK_ULONG key_size = 0; - CK_BYTE value[32]; + CK_BYTE value[64]; CK_ATTRIBUTE rsa_publ_tmpl[] = { {CKA_MODULUS, modulus, sizeof(modulus) }, {CKA_PUBLIC_EXPONENT, publ_exp, sizeof(publ_exp) }, @@ -980,14 +1015,14 @@ if (!keysize_supported(slot_id1, tsuite->wrapping_key_gen_mech.mechanism, tsuite->rsa_modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", slot_id1, tsuite->rsa_modbits); goto testcase_cleanup; } if (!keysize_supported(slot_id2, tsuite->wrapping_key_gen_mech.mechanism, tsuite->rsa_modbits)) { - testcase_skip("Token in slot %ld cannot be used with modbits.='%ld'", + testcase_skip("Token in slot %lu cannot be used with modbits='%lu'", slot_id2, tsuite->rsa_modbits); goto testcase_cleanup; } @@ -1036,14 +1071,15 @@ break; case CKM_AES_KEY_GEN: - key_size = 32; + key_size = tsuite->sym_keylen; rc = funcs->C_GenerateRandom(session2, key, key_size); if (rc != CKR_OK) { testcase_error("C_GenerateRandom(), rc=%s.", p11_get_ckr(rc)); goto testcase_cleanup; } - rc = create_AESKey(session2, CK_TRUE, key, key_size, &sym_wrap_key2); + rc = create_AESKey(session2, CK_TRUE, key, key_size, CKK_AES, + &sym_wrap_key2); if (rc == CKR_POLICY_VIOLATION) { testcase_skip("AES key import is not allowed by policy"); rc = CKR_OK; @@ -1051,6 +1087,23 @@ } break; + case CKM_AES_XTS_KEY_GEN: + key_size = tsuite->sym_keylen; + rc = funcs->C_GenerateRandom(session2, key, key_size); + if (rc != CKR_OK) { + testcase_error("C_GenerateRandom(), rc=%s.", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + rc = create_AESKey(session2, CK_TRUE, key, key_size, CKK_AES_XTS, + &sym_wrap_key2); + if (rc == CKR_POLICY_VIOLATION) { + testcase_skip("AES-XTS key import is not allowed by policy"); + rc = CKR_OK; + goto testcase_cleanup; + } + break; + case CKM_DES3_KEY_GEN: key_size = 24; rc = funcs->C_GenerateRandom(session2, key, key_size); @@ -1131,7 +1184,15 @@ sym_tmpl[0].ulValueLen = key_size; rc = create_AESKey(session1, CK_TRUE, sym_tmpl[0].pValue, sym_tmpl[0].ulValueLen, - &sym_wrap_key1); + CKK_AES, &sym_wrap_key1); + break; + + case CKM_AES_XTS_KEY_GEN: + memcpy(sym_tmpl[0].pValue, key, key_size); + sym_tmpl[0].ulValueLen = key_size; + + rc = create_AESKey(session1, CK_TRUE, sym_tmpl[0].pValue, sym_tmpl[0].ulValueLen, + CKK_AES_XTS, &sym_wrap_key1); break; case CKM_DES3_KEY_GEN: @@ -1180,6 +1241,18 @@ /* Wrap/unwrap different keys with this wrapping key */ for (i = 0; i< NUM_WRAPPED_KEY_TESTS; i++) { + /* Some combinations can not work due to size restrictions */ + if (wrapped_key_tests[i].wrapped_key_gen_mech.mechanism == CKM_AES_XTS_KEY_GEN && + ((tsuite->wrapping_mech.mechanism == CKM_RSA_PKCS && + tsuite->rsa_modbits <= 512) || + (tsuite->wrapping_mech.mechanism == CKM_RSA_PKCS_OAEP && + tsuite->rsa_modbits <= 1024))) + continue; + + if (wrapped_key_tests[i].wrapped_key_gen_mech.mechanism == CKM_DES_KEY_GEN && + tsuite->wrapping_mech.mechanism == CKM_AES_XTS) + continue; + rc = do_wrap_key_test(&wrapped_key_tests[i], &tsuite->wrapping_mech); if (rc != CKR_OK) break; @@ -1223,7 +1296,7 @@ return rc; } -CK_RV do_tok2tok_tests() +CK_RV do_tok2tok_tests(void) { CK_ULONG i; CK_RV rc; diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/tok_obj2.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/tok_obj2.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/tok_obj2.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/tok_obj2.c 2023-02-13 09:22:42.000000000 +0100 @@ -30,7 +30,7 @@ void show_error(CK_BYTE * str, CK_RV rc) { - printf("%s returned: %ld - %s\n", str, rc, p11_get_ckr(rc)); + printf("%s returned: %lu - %s\n", str, rc, p11_get_ckr(rc)); } int do_GetFunctionList(void) @@ -209,7 +209,7 @@ rc = FALSE; goto done; } - printf("Found: %d objects\n", find_count); + printf("Found: %lu objects\n", find_count); } while (find_count != 0); rc = funcs->C_FindObjectsFinal(h_session); @@ -369,7 +369,7 @@ for (i = 0; i < find_count; i++) { rc = funcs->C_DestroyObject(h_session, obj_list[i]); if (rc != CKR_OK) { - printf(" C_DestroyObject #%d returned", i); + printf(" C_DestroyObject #%lu returned", i); show_error(" ", rc); rc = FALSE; goto done; @@ -395,7 +395,7 @@ int do_inittoken(void) { - CK_BYTE label[32]; + CK_BYTE label[32 + 1]; CK_BYTE so_pin[DEFAULT_SO_PIN_LEN]; CK_ULONG so_pin_len; int len; @@ -411,7 +411,7 @@ scanf("%32s", label); printf("\nLabel is %s:", label); - for (len = 0; len < 31; len++) { + for (len = 0; len < 32; len++) { if (label[len] == '\0') { label[len] = ' '; break; @@ -517,17 +517,17 @@ printf(" manufacturerID: %32.32s\n", info.manufacturerID); printf(" model: %16.16s\n", info.model); printf(" serialNumber: %16.16s\n", info.serialNumber); - printf(" flags: %0x\n", info.flags); - printf(" ulMaxSessionCount: %d\n", info.ulMaxSessionCount); - printf(" ulSessionCount: %d\n", info.ulSessionCount); - printf(" ulMaxRwSessionCount: %d\n", info.ulMaxRwSessionCount); - printf(" ulRwSessionCount: %d\n", info.ulRwSessionCount); - printf(" ulMaxPinLen: %d\n", info.ulMaxPinLen); - printf(" ulMinPinLen: %d\n", info.ulMinPinLen); - printf(" ulTotalPublicMemory: %d\n", info.ulTotalPublicMemory); - printf(" ulFreePublicMemory: %d\n", info.ulFreePublicMemory); - printf(" ulTotalPrivateMemory: %d\n", info.ulTotalPrivateMemory); - printf(" ulFreePrivateMemory: %d\n", info.ulFreePrivateMemory); + printf(" flags: %0lx\n", info.flags); + printf(" ulMaxSessionCount: %lu\n", info.ulMaxSessionCount); + printf(" ulSessionCount: %lu\n", info.ulSessionCount); + printf(" ulMaxRwSessionCount: %lu\n", info.ulMaxRwSessionCount); + printf(" ulRwSessionCount: %lu\n", info.ulRwSessionCount); + printf(" ulMaxPinLen: %lu\n", info.ulMaxPinLen); + printf(" ulMinPinLen: %lu\n", info.ulMinPinLen); + printf(" ulTotalPublicMemory: %lu\n", info.ulTotalPublicMemory); + printf(" ulFreePublicMemory: %lu\n", info.ulFreePublicMemory); + printf(" ulTotalPrivateMemory: %lu\n", info.ulTotalPrivateMemory); + printf(" ulFreePrivateMemory: %lu\n", info.ulFreePrivateMemory); printf(" hardwareVersion: %d.%d\n", info.hardwareVersion.major, info.hardwareVersion.minor); printf(" firmwareVersion: %d.%d\n", info.firmwareVersion.major, diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/tok_obj.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/tok_obj.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/tok_obj.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/tok_obj.c 2023-02-13 09:22:42.000000000 +0100 @@ -191,7 +191,7 @@ goto done; } - printf("Found: %ld objects\n", find_count); + printf("Found: %lu objects\n", find_count); rc = TRUE; done: @@ -343,7 +343,7 @@ for (i = 0; i < find_count; i++) { rc = funcs->C_DestroyObject(h_session, obj_list[i]); if (rc != CKR_OK) { - printf(" C_DestroyObject #%ld returned", i); + printf(" C_DestroyObject #%lu returned", i); show_error(" ", rc); rc = FALSE; goto done; @@ -501,16 +501,16 @@ printf(" model: %16.16s\n", info.model); printf(" serialNumber: %16.16s\n", info.serialNumber); printf(" flags: %p\n", (void *) info.flags); - printf(" ulMaxSessionCount: %ld\n", info.ulMaxSessionCount); - printf(" ulSessionCount: %ld\n", info.ulSessionCount); - printf(" ulMaxRwSessionCount: %ld\n", info.ulMaxRwSessionCount); - printf(" ulRwSessionCount: %ld\n", info.ulRwSessionCount); - printf(" ulMaxPinLen: %ld\n", info.ulMaxPinLen); - printf(" ulMinPinLen: %ld\n", info.ulMinPinLen); - printf(" ulTotalPublicMemory: %ld\n", info.ulTotalPublicMemory); - printf(" ulFreePublicMemory: %ld\n", info.ulFreePublicMemory); - printf(" ulTotalPrivateMemory: %ld\n", info.ulTotalPrivateMemory); - printf(" ulFreePrivateMemory: %ld\n", info.ulFreePrivateMemory); + printf(" ulMaxSessionCount: %lu\n", info.ulMaxSessionCount); + printf(" ulSessionCount: %lu\n", info.ulSessionCount); + printf(" ulMaxRwSessionCount: %lu\n", info.ulMaxRwSessionCount); + printf(" ulRwSessionCount: %lu\n", info.ulRwSessionCount); + printf(" ulMaxPinLen: %lu\n", info.ulMaxPinLen); + printf(" ulMinPinLen: %lu\n", info.ulMinPinLen); + printf(" ulTotalPublicMemory: %lu\n", info.ulTotalPublicMemory); + printf(" ulFreePublicMemory: %lu\n", info.ulFreePublicMemory); + printf(" ulTotalPrivateMemory: %lu\n", info.ulTotalPrivateMemory); + printf(" ulFreePrivateMemory: %lu\n", info.ulFreePrivateMemory); printf(" hardwareVersion: %d.%d\n", info.hardwareVersion.major, info.hardwareVersion.minor); printf(" firmwareVersion: %d.%d\n", info.firmwareVersion.major, diff -Nru opencryptoki-3.18.0+dfsg/testcases/misc_tests/tok_rsa.c opencryptoki-3.20.0+dfsg/testcases/misc_tests/tok_rsa.c --- opencryptoki-3.18.0+dfsg/testcases/misc_tests/tok_rsa.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/misc_tests/tok_rsa.c 2023-02-13 09:22:42.000000000 +0100 @@ -306,7 +306,7 @@ bits = 512; if (bits >= rsakeygeninfo.ulMinKeySize && bits <= rsakeygeninfo.ulMaxKeySize) { - sprintf((char *)label, "XXX DELETE ME TEST LABEL %dbit", bits); + sprintf((char *)label, "XXX DELETE ME TEST LABEL %ubit", bits); rv = do_GenerateTokenRSAKeyPair(session, label, bits); if (rv != CKR_OK) { show_error("do_GenerateTokenRSAKeyPair(512)", rv); @@ -319,7 +319,7 @@ bits = 1024; if (bits >= rsakeygeninfo.ulMinKeySize && bits <= rsakeygeninfo.ulMaxKeySize) { - sprintf((char *)label, "XXX DELETE ME TEST LABEL %dbit", bits); + sprintf((char *)label, "XXX DELETE ME TEST LABEL %ubit", bits); rv = do_GenerateTokenRSAKeyPair(session, label, bits); if (rv != CKR_OK) { show_error("do_GenerateTokenRSAKeyPair(1024)", rv); @@ -332,7 +332,7 @@ bits = 2048; if (bits >= rsakeygeninfo.ulMinKeySize && bits <= rsakeygeninfo.ulMaxKeySize) { - sprintf((char *)label, "XXX DELETE ME TEST LABEL %dbit", bits); + sprintf((char *)label, "XXX DELETE ME TEST LABEL %ubit", bits); rv = do_GenerateTokenRSAKeyPair(session, label, bits); if (rv != CKR_OK) { show_error("do_GenerateTokenRSAKeyPair(2048)", rv); @@ -345,7 +345,7 @@ bits = 4096; if (bits >= rsakeygeninfo.ulMinKeySize && bits <= rsakeygeninfo.ulMaxKeySize) { - sprintf((char *)label, "XXX DELETE ME TEST LABEL %dbit", bits); + sprintf((char *)label, "XXX DELETE ME TEST LABEL %ubit", bits); rv = do_GenerateTokenRSAKeyPair(session, label, bits); if (rv != CKR_OK) { show_error("do_GenerateTokenRSAKeyPair(4096)", rv); @@ -388,7 +388,7 @@ bits = 512; if (bits >= rsakeygeninfo.ulMinKeySize && bits <= rsakeygeninfo.ulMaxKeySize) { - sprintf((char *)label, "XXX DELETE ME TEST LABEL %dbit", bits); + sprintf((char *)label, "XXX DELETE ME TEST LABEL %ubit", bits); rv = do_VerifyTokenRSAKeyPair(session, label, bits); if (rv != CKR_OK) { show_error("do_VerifyTokenRSAKeyPair(512)", rv); @@ -399,7 +399,7 @@ bits = 1024; if (bits >= rsakeygeninfo.ulMinKeySize && bits <= rsakeygeninfo.ulMaxKeySize) { - sprintf((char *)label, "XXX DELETE ME TEST LABEL %dbit", bits); + sprintf((char *)label, "XXX DELETE ME TEST LABEL %ubit", bits); rv = do_VerifyTokenRSAKeyPair(session, label, 1024); if (rv != CKR_OK) { show_error("do_VerifyTokenRSAKeyPair(1024)", rv); @@ -410,7 +410,7 @@ bits = 2048; if (bits >= rsakeygeninfo.ulMinKeySize && bits <= rsakeygeninfo.ulMaxKeySize) { - sprintf((char *)label, "XXX DELETE ME TEST LABEL %dbit", bits); + sprintf((char *)label, "XXX DELETE ME TEST LABEL %ubit", bits); rv = do_VerifyTokenRSAKeyPair(session, label, bits); if (rv != CKR_OK) { show_error("do_VerifyTokenRSAKeyPair(2048)", rv); @@ -421,7 +421,7 @@ bits = 4096; if (bits >= rsakeygeninfo.ulMinKeySize && bits <= rsakeygeninfo.ulMaxKeySize) { - sprintf((char *)label, "XXX DELETE ME TEST LABEL %dbit", bits); + sprintf((char *)label, "XXX DELETE ME TEST LABEL %ubit", bits); rv = do_VerifyTokenRSAKeyPair(session, label, bits); if (rv != CKR_OK) { show_error("do_VerifyTokenRSAKeyPair(4096)", rv); diff -Nru opencryptoki-3.18.0+dfsg/testcases/ock_tests.sh.in opencryptoki-3.20.0+dfsg/testcases/ock_tests.sh.in --- opencryptoki-3.18.0+dfsg/testcases/ock_tests.sh.in 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/ock_tests.sh.in 2023-02-13 09:22:42.000000000 +0100 @@ -54,6 +54,7 @@ OCK_TESTS+=" misc_tests/fork misc_tests/obj_mgmt_tests" OCK_TESTS+=" misc_tests/obj_mgmt_lock_tests misc_tests/reencrypt" OCK_TESTS+=" misc_tests/events misc_tests/cca_export_import_test" +OCK_TESTS+=" misc_tests/dual_functions" OCK_TEST="" OCK_BENCHS="pkcs11/*bench" @@ -94,19 +95,6 @@ } ### -## check_ccatok() - Check if stuff needed by the CCA token -## are present -### -check_ccatok() -{ - # Check if catcher.exe is running - if ! pgrep catcher.exe; then - echo "Error: catcher.exe daemon not running" - return 1 - fi -} - -### ## init_slot() - Initialize a specific slot ## $1 - The slot number to initialize ## @@ -154,7 +142,6 @@ ;; *CCA*) echo "CCA Token type detected" - check_ccatok || return TOKTYPE="CCA" ;; *ICA*) diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/attribute.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/attribute.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/attribute.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/attribute.c 2023-02-13 09:22:42.000000000 +0100 @@ -476,6 +476,115 @@ return rc; } +CK_RV do_TestAttributesAESXTS(void) +{ + CK_OBJECT_HANDLE obj_handle = CK_INVALID_HANDLE; + CK_SESSION_HANDLE session; + CK_RV rc = 0, rv = 0; + CK_FLAGS flags; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len; + + CK_BYTE key[] = { + 0xa5, 0x6e, 0x4a, 0x0e, 0x70, 0x10, 0x17, 0x58, + 0x9a, 0x51, 0x87, 0xdc, 0x7e, 0xa8, 0x41, 0xd1, + 0x56, 0xf2, 0xec, 0x0e, 0x36, 0xad, 0x52, 0xa4, + 0x4d, 0xfe, 0xb1, 0xe6, 0x1f, 0x7a, 0xd9, 0x91, + 0xd8, 0xc5, 0x10, 0x56, 0xff, 0xed, 0xb1, 0x62, + 0xb4, 0xc0, 0xf2, 0x83, 0xa1, 0x2a, 0x88, 0xa3, + 0x94, 0xdf, 0xf5, 0x26, 0xab, 0x72, 0x91, 0xcb, + 0xb3, 0x07, 0xce, 0xab, 0xfc, 0xe0, 0xb1, 0xdf, + }; + + int keylen = 64; + + CK_OBJECT_CLASS class = CKO_SECRET_KEY; + CK_KEY_TYPE keyType = CKK_AES_XTS; + CK_CHAR label[] = "An AES XTS key object"; + CK_BBOOL false = FALSE; + CK_BBOOL true = TRUE; + CK_BBOOL boolval; + + CK_ATTRIBUTE keyTemplate[] = { + {CKA_CLASS, &class, sizeof(class)}, + {CKA_KEY_TYPE, &keyType, sizeof(keyType)}, + {CKA_TOKEN, &false, sizeof(false)}, + {CKA_LABEL, label, sizeof(label) - 1}, + {CKA_VALUE, key, keylen}, + {CKA_EXTRACTABLE, &false, sizeof(CK_BBOOL)}, + {CKA_IBM_PROTKEY_EXTRACTABLE, &true, sizeof(CK_BBOOL)}, + }; + CK_ULONG keyTemplate_len = sizeof(keyTemplate) / sizeof(CK_ATTRIBUTE); + + CK_ATTRIBUTE new_attrs[] = { + {CKA_ENCRYPT, &false, sizeof(false)}, + }; + + CK_ATTRIBUTE verify_attrs[] = { + {CKA_ENCRYPT, &boolval, sizeof(boolval)}, + }; + + testcase_begin(""); + testcase_rw_session(); + testcase_user_login(); + + /** skip test if the slot doesn't support this mechanism **/ + if (!mech_supported(SLOT_ID, CKM_AES_XTS)) { + testcase_skip("Skip test as CKM_AES_XTS not supported"); + goto testcase_cleanup; + } + + /* create a aes xts key object */ + rc = funcs->C_CreateObject(session, keyTemplate, keyTemplate_len, &obj_handle); + if (rc != CKR_OK) { + if (is_rejected_by_policy(rc, session)) { + testcase_skip("Key generation is not allowed by policy"); + goto testcase_cleanup; + } + testcase_fail("C_CreateObject() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* Now add new attributes */ + testcase_new_assertion(); + rc = funcs->C_SetAttributeValue(session, obj_handle, new_attrs, 1); + if (rc != CKR_OK) { + testcase_fail("C_SetAttributeValue() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + testcase_pass("Successfully added new attribute."); + + /* Now get the attributes that were updated */ + testcase_new_assertion(); + rc = funcs->C_GetAttributeValue(session, obj_handle, verify_attrs, 1); + if (rc != CKR_OK) { + testcase_fail("C_GetAttributeValue() rc = %s", p11_get_ckr(rc)); + goto testcase_cleanup; + } + + /* verify the attribute values retrieved */ + if (*(CK_BBOOL *) verify_attrs[0].pValue != false) { + testcase_fail("CKA_ENCRYPT mismatch"); + goto testcase_cleanup; + } + testcase_pass("Successfully verified newly added attribute."); + +testcase_cleanup: + if (obj_handle != CK_INVALID_HANDLE) { + rv = funcs->C_DestroyObject(session, obj_handle); + if (rv != CKR_OK) + testcase_error("C_DestroyObject rv=%s", p11_get_ckr(rv)); + } + + testcase_user_logout(); + rv = funcs->C_CloseSession(session); + if (rv != CKR_OK) + testcase_error("C_CloseSessions rv=%s", p11_get_ckr(rv)); + + return rc; +} + int main(int argc, char **argv) { int rc; @@ -514,6 +623,7 @@ testcase_setup(); rc = do_TestAttributes(); + rc = do_TestAttributesAESXTS(); testcase_print_result(); funcs->C_Finalize(NULL); diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/copyobjects.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/copyobjects.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/copyobjects.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/copyobjects.c 2023-02-13 09:22:42.000000000 +0100 @@ -373,7 +373,7 @@ if (rv != CKR_FUNCTION_NOT_PARALLEL) return rv; - rc = funcs->C_CancelFunction(hsess); + rv = funcs->C_CancelFunction(hsess); if (rv != CKR_FUNCTION_NOT_PARALLEL) return rv; } diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/destroyobjects.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/destroyobjects.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/destroyobjects.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/destroyobjects.c 2023-02-13 09:22:42.000000000 +0100 @@ -37,7 +37,7 @@ CK_ULONG user_pin_len; CK_OBJECT_HANDLE keyobj[8]; CK_OBJECT_HANDLE obj_list[10]; - CK_OBJECT_HANDLE keyobj_no_destroy; + CK_OBJECT_HANDLE keyobj_no_destroy = CK_INVALID_HANDLE; CK_ULONG i, num_objs = 0, find_count, found = 0; CK_MECHANISM mech; CK_BBOOL false = CK_FALSE; diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/generate_keypair.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/generate_keypair.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/generate_keypair.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/generate_keypair.c 2023-02-13 09:22:42.000000000 +0100 @@ -103,7 +103,7 @@ if (!mech_supported(SLOT_ID, CKM_RSA_PKCS_KEY_PAIR_GEN)) { testcase_skip("Mechanism CKM_RSA_PKCS_KEY_PAIR_GEN is not supported with slot " - "%ld. Skipping key check", SLOT_ID); + "%lu. Skipping key check", SLOT_ID); goto testcase_cleanup; } diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/getobjectsize.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/getobjectsize.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/getobjectsize.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/getobjectsize.c 2023-02-13 09:22:42.000000000 +0100 @@ -133,19 +133,19 @@ { CK_SESSION_HANDLE hsess = 0; - rc = funcs->C_GetFunctionStatus(hsess); - if (rc != CKR_FUNCTION_NOT_PARALLEL) - return rc; + rv = funcs->C_GetFunctionStatus(hsess); + if (rv != CKR_FUNCTION_NOT_PARALLEL) + return rv; - rc = funcs->C_CancelFunction(hsess); - if (rc != CKR_FUNCTION_NOT_PARALLEL) - return rc; + rv = funcs->C_CancelFunction(hsess); + if (rv != CKR_FUNCTION_NOT_PARALLEL) + return rv; } - rc = do_GetObjectSize(); + rv = do_GetObjectSize(); funcs->C_Finalize(NULL); /* make sure we return non-zero if rv is non-zero */ - return ((rv == 0) || (rv % 256) ? (int)rv : -1); + return testcase_return(rv); } diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/hw_fn.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/hw_fn.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/hw_fn.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/hw_fn.c 2023-02-13 09:22:42.000000000 +0100 @@ -186,7 +186,7 @@ */ if (find_count != 2) { printf("%s:%d ERROR: C_FindObjects #1 should have found 2 objects!\n" - " It found %ld objects\n", __FILE__, __LINE__, + " It found %lu objects\n", __FILE__, __LINE__, find_count); rc = -1; goto done; @@ -230,7 +230,7 @@ if (find_count != 1) { printf("%s:%d ERROR: C_FindObjects #2 should have found 1 object!\n" - " It found %ld objects\n", __FILE__, __LINE__, + " It found %lu objects\n", __FILE__, __LINE__, find_count); funcs->C_FindObjectsFinal(sess); rc = -1; @@ -292,7 +292,7 @@ } } - printf("Using slot %ld...\n\n", slot_id); + printf("Using slot %lu...\n\n", slot_id); if (!do_GetFunctionList()) return -1; diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/sess_mgmt.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/sess_mgmt.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/sess_mgmt.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/sess_mgmt.c 2023-02-13 09:22:42.000000000 +0100 @@ -25,7 +25,7 @@ void dump_session_info(CK_SESSION_INFO * info) { printf(" CK_SESSION_INFO:\n"); - printf(" slotID: %ld\n", info->slotID); + printf(" slotID: %lu\n", info->slotID); printf(" state: "); switch (info->state) { case CKS_RO_PUBLIC_SESSION: @@ -44,8 +44,8 @@ printf("CKS_RW_SO_FUNCTIONS\n"); break; } - printf(" flags: %p\n", (void *) info->flags); - printf(" ulDeviceError: %ld\n", info->ulDeviceError); + printf(" flags: 0x%lx\n", info->flags); + printf(" ulDeviceError: %lu\n", info->ulDeviceError); } CK_RV do_OpenSession(void) @@ -577,6 +577,13 @@ // save session #1's operation state rc = funcs->C_GetOperationState(session1, NULL, &op_state_len); if (rc != CKR_OK) { + if (rc == CKR_STATE_UNSAVEABLE) { + printf("Session state not savable for mechanism %s. (skipped)\n", + mech_to_str(mech.mechanism)); + funcs->C_CloseSession(session1); + funcs->C_CloseSession(session2); + return 0; + } show_error(" C_GetOperationState #1", rc); return rc; } @@ -670,9 +677,9 @@ CK_RV rc; CK_BYTE original[1024]; - CK_BYTE digest1[16]; - CK_BYTE digest2[16]; - CK_BYTE digest3[16]; + CK_BYTE digest1[32]; + CK_BYTE digest2[32]; + CK_BYTE digest3[32]; CK_ULONG orig_len; CK_ULONG digest1_len, digest2_len, digest3_len; @@ -739,7 +746,7 @@ for (i = 0; i < orig_len; i++) original[i] = i % 255; - mech.mechanism = CKM_MD5; + mech.mechanism = CKM_SHA256; mech.pParameter = NULL; mech.ulParameterLen = 0; @@ -793,6 +800,14 @@ // save the operation states of sessions 1 and 2 rc = funcs->C_GetOperationState(session1, NULL, &op_state1_len); if (rc != CKR_OK) { + if (rc == CKR_STATE_UNSAVEABLE) { + printf("Session state not savable for mechanism %s. (skipped)\n", + mech_to_str(mech.mechanism)); + funcs->C_CloseSession(session1); + funcs->C_CloseSession(session2); + funcs->C_CloseSession(session3); + return 0; + } show_error(" C_GetOperationState #1", rc); return rc; } @@ -811,6 +826,14 @@ rc = funcs->C_GetOperationState(session2, NULL, &op_state2_len); if (rc != CKR_OK) { + if (rc == CKR_STATE_UNSAVEABLE) { + printf("Session state not savable for mechanism %s. (skipped)\n", + mech_to_str(mech.mechanism)); + funcs->C_CloseSession(session1); + funcs->C_CloseSession(session2); + funcs->C_CloseSession(session3); + return 0; + } show_error(" C_GetOperationState #3", rc); return rc; } @@ -917,9 +940,9 @@ CK_RV rc; CK_BYTE original[1024]; - CK_BYTE digest1[16]; - CK_BYTE digest2[16]; - CK_BYTE digest3[16]; + CK_BYTE digest1[32]; + CK_BYTE digest2[32]; + CK_BYTE digest3[32]; CK_BYTE junk[1024]; CK_ULONG orig_len, junk_len; @@ -1028,7 +1051,7 @@ return rc; } - mech2.mechanism = CKM_MD5; + mech2.mechanism = CKM_SHA256; mech2.pParameter = NULL; mech2.ulParameterLen = 0; @@ -1069,6 +1092,14 @@ rc = funcs->C_GetOperationState(session2, NULL, &op_state2_len); if (rc != CKR_OK) { + if (rc == CKR_STATE_UNSAVEABLE) { + printf("Session state not savable for mechanism %s. (skipped)\n", + mech_to_str(mech2.mechanism)); + funcs->C_CloseSession(session1); + funcs->C_CloseSession(session2); + funcs->C_CloseSession(session3); + return 0; + } show_error(" C_GetOperationState #1", rc); return rc; } @@ -1166,7 +1197,171 @@ return rc; } -CK_RV sess_mgmt_functions() +CK_RV do_SessionCancel(void) +{ + CK_SLOT_ID slot_id; + CK_SESSION_HANDLE session1; + CK_FLAGS flags; + CK_BYTE user_pin[PKCS11_MAX_PIN_LEN]; + CK_ULONG user_pin_len; + CK_RV rc; + + CK_BYTE original[1024]; + CK_BYTE crypt1[1024]; + CK_BYTE crypt2[1024]; + CK_BYTE trash1[8]; + CK_BYTE trash2[8]; + + CK_ULONG orig_len, crypt1_len, crypt2_len, trash1_len, trash2_len; + CK_ULONG i; + + CK_ULONG key_len = 16; + CK_ATTRIBUTE key_gen_tmpl[] = { + {CKA_VALUE_LEN, &key_len, sizeof(CK_ULONG)} + }; + + CK_MECHANISM mech; + CK_OBJECT_HANDLE h_key; + + printf("do_SessionCancel...\n"); + slot_id = SLOT_ID; + + // create two USER RW sessions + flags = CKF_SERIAL_SESSION | CKF_RW_SESSION; + rc = funcs->C_OpenSession(slot_id, flags, NULL, NULL, &session1); + if (rc != CKR_OK) { + show_error(" C_OpenSession #1", rc); + return rc; + } + + if (get_user_pin(user_pin)) + return CKR_FUNCTION_FAILED; + + user_pin_len = (CK_ULONG) strlen((char *) user_pin); + + rc = funcs->C_Login(session1, CKU_USER, user_pin, user_pin_len); + if (rc != CKR_OK) { + show_error(" C_Login #1", rc); + return rc; + } + + orig_len = sizeof(original); + for (i = 0; i < orig_len; i++) + original[i] = i % 255; + + trash1_len = sizeof(trash1); + memcpy(trash1, "asdflkjasdlkjadslkj", trash1_len); + + // first generate a AES key + mech.mechanism = CKM_AES_KEY_GEN; + mech.ulParameterLen = 0; + mech.pParameter = NULL; + + if (!mech_supported(slot_id, mech.mechanism)) { + printf("Mechanism %s not supported. (skipped)\n", + mech_to_str(mech.mechanism)); + funcs->C_CloseSession(session1); + return 0; + } + + rc = funcs->C_GenerateKey(session1, &mech, key_gen_tmpl, 1, &h_key); + if (rc != CKR_OK) { + show_error(" C_GenerateKey #1", rc); + return rc; + } + // now encrypt the original data all at once using CBC + mech.mechanism = CKM_AES_CBC; + mech.ulParameterLen = 16; + mech.pParameter = "1234qwerasdfyxcv"; + + rc = funcs->C_EncryptInit(session1, &mech, h_key); + if (rc != CKR_OK) { + show_error(" C_EncryptInit #1", rc); + return rc; + } + + // cancel the encrypt session + rc = funcs3->C_SessionCancel(session1, CKF_ENCRYPT); + if (rc != CKR_OK) { + show_error(" C_SessionCancel #1", rc); + return rc; + } + + crypt1_len = sizeof(crypt1); + rc = funcs->C_Encrypt(session1, original, orig_len, crypt1, &crypt1_len); + if (rc != CKR_OPERATION_NOT_INITIALIZED) { + show_error(" C_Encrypt #1", rc); + return rc; + } + + // now, begin encrypting multipart + rc = funcs->C_EncryptInit(session1, &mech, h_key); + if (rc != CKR_OK) { + show_error(" C_EncryptInit #2", rc); + return rc; + } + + // cancel non existing sign session (no effect expected) + rc = funcs3->C_SessionCancel(session1, CKF_SIGN); + if (rc != CKR_OK) { + show_error(" C_SessionCancel #2", rc); + return rc; + } + + crypt2_len = sizeof(crypt2); + rc = funcs->C_EncryptUpdate(session1, original, orig_len / 2, + crypt2, &crypt2_len); + if (rc != CKR_OK) { + show_error(" C_EncryptUpdate #1", rc); + return rc; + } + + // cancel non existing decrypt session (no effect expected) + rc = funcs3->C_SessionCancel(session1, CKF_DECRYPT); + if (rc != CKR_OK) { + show_error(" C_SessionCancel #3", rc); + return rc; + } + + // now, encrypt the rest of the original data + i = crypt2_len; + crypt2_len = sizeof(crypt2) - crypt2_len; + rc = funcs->C_EncryptUpdate(session1, + original + orig_len / 2, orig_len / 2, + crypt2 + i, &crypt2_len); + if (rc != CKR_OK) { + show_error(" C_EncryptUpdate #3", rc); + return rc; + } + + crypt2_len += i; + + // cancel non existing find session (no effect expected) + rc = funcs3->C_SessionCancel(session1, CKF_FIND_OBJECTS); + if (rc != CKR_OK) { + show_error(" C_SessionCancel #3", rc); + return rc; + } + + trash2_len = sizeof(trash2); + rc = funcs->C_EncryptFinal(session1, trash2, &trash2_len); + if (rc != CKR_OK) { + show_error(" C_EncryptFinal #1", rc); + return rc; + } + + rc = funcs->C_CloseSession(session1); + if (rc != CKR_OK) { + show_error(" C_CloseSession #1", rc); + return rc; + } + + printf("Looks okay...\n"); + + return rc; +} + +CK_RV sess_mgmt_functions(void) { SYSTEMTIME t1, t2; CK_RV rc; @@ -1232,6 +1427,13 @@ if (rc && !no_stop) return rc; GetSystemTime(&t2); + process_time(t1, t2); + + GetSystemTime(&t1); + rc = do_SessionCancel(); + if (rc && !no_stop) + return rc; + GetSystemTime(&t2); process_time(t1, t2); return rc; diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/sess_opstate.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/sess_opstate.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/sess_opstate.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/sess_opstate.c 2023-02-13 09:22:42.000000000 +0100 @@ -29,7 +29,7 @@ CK_RV rc; CK_BYTE_PTR ptr = malloc(nbytes); if (ptr == NULL) { - testcase_error("malloc(%lu) failed", nbytes); + testcase_error("malloc(%ld) failed", nbytes); return NULL; } @@ -77,7 +77,7 @@ if (!mech_supported(SLOT_ID, mech1.mechanism)) { testcase_skip("Mechanism CKM_SHA256 is not supported with slot " - "%ld. Skipping key check", SLOT_ID); + "%lu. Skipping key check", SLOT_ID); goto out; } @@ -133,6 +133,7 @@ if (rc != CKR_OK) { if (rc == CKR_STATE_UNSAVEABLE) { testcase_skip("Get/SetOperationState digest test: state unsavable"); + rc = CKR_OK; goto out; } testcase_error("C_GetOperationState rc=%s", p11_get_ckr(rc)); @@ -149,6 +150,7 @@ if (rc != CKR_OK) { if (rc == CKR_STATE_UNSAVEABLE) { testcase_skip("Get/SetOperationState digest test: state unsavable"); + rc = CKR_OK; goto out; } testcase_error("C_GetOperationState rc=%s", p11_get_ckr(rc)); @@ -169,7 +171,7 @@ if (!mech_supported(SLOT_ID, mech2.mechanism)) { testcase_skip("Mechanism CKM_SHA_1 is not supported with slot " - "%ld. Skipping key check", SLOT_ID); + "%lu. Skipping key check", SLOT_ID); continue; } diff -Nru opencryptoki-3.18.0+dfsg/testcases/pkcs11/sess_perf.c opencryptoki-3.20.0+dfsg/testcases/pkcs11/sess_perf.c --- opencryptoki-3.18.0+dfsg/testcases/pkcs11/sess_perf.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/pkcs11/sess_perf.c 2023-02-13 09:22:42.000000000 +0100 @@ -33,7 +33,7 @@ void dump_session_info(CK_SESSION_INFO * info) { printf(" CK_SESSION_INFO:\n"); - printf(" slotID: %ld\n", info->slotID); + printf(" slotID: %lu\n", info->slotID); printf(" state: "); switch (info->state) { case CKS_RO_PUBLIC_SESSION: @@ -52,8 +52,8 @@ printf("CKS_RW_SO_FUNCTIONS\n"); break; } - printf(" flags: %p\n", (void *) info->flags); - printf(" ulDeviceError: %ld\n", info->ulDeviceError); + printf(" flags: 0x%lx\n", info->flags); + printf(" ulDeviceError: %lu\n", info->ulDeviceError); } int create_des_encrypt_context(CK_SESSION_HANDLE_PTR hsess, diff -Nru opencryptoki-3.18.0+dfsg/testcases/policy/policytest.c opencryptoki-3.20.0+dfsg/testcases/policy/policytest.c --- opencryptoki-3.18.0+dfsg/testcases/policy/policytest.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/policy/policytest.c 2023-02-13 09:22:42.000000000 +0100 @@ -264,7 +264,7 @@ &pubkey, &privkey); } -static CK_RV generateAESKey() +static CK_RV generateAESKey(void) { CK_OBJECT_HANDLE key; CK_ULONG keylen = POLICY_TEST_AES_SIZE / 8; diff -Nru opencryptoki-3.18.0+dfsg/testcases/unit/buffertest.c opencryptoki-3.20.0+dfsg/testcases/unit/buffertest.c --- opencryptoki-3.18.0+dfsg/testcases/unit/buffertest.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/testcases/unit/buffertest.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,123 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ +#include +#include +#include + +#include +#include "unittest.h" + +#define STDERR_RC_UNEXP(n, func, rc, exp_rc) \ + fprintf(stderr, "[%d] %s: %s (curr: %ld, expected: %ld)\n", \ + n, func, "unexpected return value", rc, exp_rc) + +static char *short_string = "abc"; +static char *long_string = "abcdefghijklmnopqrstuvwxyz" + "ABCDEFGHIJKLMNOPQRSTUVWXYZ" + "abcdefghijklmnopqrstuvwxyz" + "ABCDEFGHIJKLMNOPQRSTUVWXYZ" + "abcdefghijklmnopqrstuvwxyz" + "ABCDEFGHIJKLMNOPQRSTUVWXYZ" + "abcdefghijklmnopqrstuvwxyz" + "ABCDEFGHIJKLMNOPQRSTUVWXYZ" + "abcdefghijklmnopqrstuvwxyz" + "ABCDEFGHIJKLMNOPQRSTUVWXYZ" + "abcdefghijklmnopqrstuvwxyz" + "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; + +static int test_buffer_api(char *s) +{ + int result = 0; + long rc, exp_rc; + size_t s_len = strlen(s); + p11_buffer_t *buf = p11_buffer_new(); + + /* check for buffer length and size */ + if ((*p11_buffer_char(buf) != '\0') || + (p11_buffer_char(buf) == NULL) || + (p11_buffer_size(buf) == 0) || + (strlen(p11_buffer_char(buf)) != 0)) { + fprintf(stderr, "[%d] %s: %s\n", + 0, "p11_buffer_new()", + "wrong initial buffer values"); + result++; + } + + /* check corner case s == NULL */ + exp_rc = strlen(p11_buffer_char(buf)); + rc = p11_buffer_append(buf, NULL); + if (rc != exp_rc) { + STDERR_RC_UNEXP(1, "p11_buffer_append()", rc, exp_rc); + result++; + } + + /* check corner case s == NULL, len == 0 */ + exp_rc = strlen(p11_buffer_char(buf)); + rc = p11_buffer_append_len(buf, NULL, 0); + if (rc != exp_rc) { + STDERR_RC_UNEXP(2, "p11_buffer_append_len()", rc, exp_rc); + result++; + } + + /* check corner case len == 0 */ + exp_rc = strlen(p11_buffer_char(buf)); + rc = p11_buffer_append_len(buf, s, 0); + if (rc != exp_rc) { + STDERR_RC_UNEXP(3, "p11_buffer_append_len()", rc, exp_rc); + result++; + } + + /* normal append */ + exp_rc = strlen(p11_buffer_char(buf)) + s_len; + rc = p11_buffer_append(buf, s); + if (rc != exp_rc) { + STDERR_RC_UNEXP(4, "p11_buffer_append()", rc, exp_rc); + result++; + } + + /* normal append with length */ + exp_rc = strlen(p11_buffer_char(buf)) + s_len; + rc = p11_buffer_append_len(buf, s, s_len); + if (rc != exp_rc) { + STDERR_RC_UNEXP(5, "p11_buffer_append()", rc, exp_rc); + result++; + } + + /* normal append with printf */ + exp_rc = strlen(p11_buffer_char(buf)) + 14 + s_len; + rc = p11_buffer_append_printf(buf, "append_prinf(%s)", s); + if (rc != exp_rc) { + STDERR_RC_UNEXP(6, "p11_buffer_append()", rc, exp_rc); + result++; + } + + /* reset buffer */ + p11_buffer_reset(buf); + if ((*p11_buffer_char(buf) != '\0') || + (strlen(p11_buffer_char(buf)) != 0)) { + fprintf(stderr, "[%d] %s: %s\n", + 7, "p11_buffer_reset()", + "wrong buffer values after reset"); + result++; + } + + p11_buffer_free(buf); + return result; +} + +int main(void) +{ + if (test_buffer_api(short_string)) + return TEST_FAIL; + if (test_buffer_api(long_string)) + return TEST_FAIL; + + return TEST_PASS; +} diff -Nru opencryptoki-3.18.0+dfsg/testcases/unit/configdump.c opencryptoki-3.20.0+dfsg/testcases/unit/configdump.c --- opencryptoki-3.18.0+dfsg/testcases/unit/configdump.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/unit/configdump.c 2023-02-13 09:22:42.000000000 +0100 @@ -17,6 +17,13 @@ static const char test7[] = "foo\n(\n bar,\n buzz\n)\n"; static const char nested1[] = "nested {\n foo (\n bar,\n buzz\n )\n}\n"; static const char nested2[] = "nested {\n foo\n (\n bar,\n buzz\n )\n}\n"; +static const char numpair1[] = "foo\n 1 2\n 3 4\nbar\n"; +static const char bare1[] = "foo\n"; +static const char bare2[] = "foo bar\n"; +static const char bare3[] = "foo\nbar\n"; +static const char bare4[] = "\"foo\"\n"; +static const char bare5[] = "\"foo\"\n\"bar\"\n"; +static const char bare6[] = "foo \"bar\"\n"; static char outbuf[1024]; static const char *curtest; @@ -74,5 +81,12 @@ runparsedumptest(test7); runparsedumptest(nested1); runparsedumptest(nested2); + runparsedumptest(numpair1); + runparsedumptest(bare1); + runparsedumptest(bare2); + runparsedumptest(bare3); + runparsedumptest(bare4); + runparsedumptest(bare5); + runparsedumptest(bare6); return TEST_PASS; } diff -Nru opencryptoki-3.18.0+dfsg/testcases/unit/pintest.c opencryptoki-3.20.0+dfsg/testcases/unit/pintest.c --- opencryptoki-3.18.0+dfsg/testcases/unit/pintest.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/testcases/unit/pintest.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,37 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ +#include +#include +#include + +#include +#include "unittest.h" + +int main(int argc, char *argv[]) +{ + const char *pin; + char *buf = NULL; + + switch(getopt(argc, argv, "pn")) { + case 'p': + pin = pin_prompt(&buf, "Enter the PIN: "); + printf("pin: %s\n", pin); + break; + case 'n': + pin = pin_prompt_new(&buf, "Enter new PIN: ", "Re-enter new PIN: "); + printf("pin: %s\n", pin); + break; + default: + break; + } + + pin_free(&buf); + return 0; +} diff -Nru opencryptoki-3.18.0+dfsg/testcases/unit/pintest.sh opencryptoki-3.20.0+dfsg/testcases/unit/pintest.sh --- opencryptoki-3.18.0+dfsg/testcases/unit/pintest.sh 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/testcases/unit/pintest.sh 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,51 @@ +#!/bin/bash +# +# COPYRIGHT (c) International Business Machines Corp. 2022 +# +# This program is provided under the terms of the Common Public License, +# version 1.0 (CPL-1.0). Any use, reproduction or distribution for this software +# constitutes recipient's acceptance of CPL-1.0 terms which can be found +# in the file LICENSE file or at https://opensource.org/licenses/cpl1.0.php + +PINTEST=testcases/unit/pintest + +# functions +print_test_result() { + local msg=$1 + local result=$2 + local result_exp=$3 + + if [ "${result}" = "${result_exp}" ]; then + printf "${msg}: PASS result: \"${result}\", expected: \"${result_exp}\"\n" + RC=0 + else + printf "${msg}: FAIL result: ${result}, expected: ${result_exp}\n" + RC=1 + fi + return $RC +} + +unset PKCS11_USER_PIN +unset PKCS11_SO_PIN + +TEST_PIN=12345678 +RESULT_PIN="pin: ${TEST_PIN}" +RESULT_ERR="pin: (null)" + +# prompt +RESULT=$(printf "${TEST_PIN}\n" | ${PINTEST} -p | tail -n1 ) +print_test_result "pin prompt" "${RESULT}" "${RESULT_PIN}" || exit 99 + +RESULT=$(printf "${TEST_PIN}\n${TEST_PIN}\n" | ${PINTEST} -n | tail -n1 ) +print_test_result "pin prompt-new" "${RESULT}" "${RESULT_PIN}" || exit 99 + +RESULT=$(printf "\n\n" | ${PINTEST} -n | tail -n1 ) +print_test_result "pin prompt-new" "${RESULT}" "${RESULT_ERR}" || exit 99 + +RESULT=$(${PINTEST} -p <&- | tail -n1 ) +print_test_result "pin prompt-user" "${RESULT}" "${RESULT_ERR}" || exit 99 + +RESULT=$(${PINTEST} -n <&- | tail -n1 ) +print_test_result "pin prompt-new" "${RESULT}" "${RESULT_ERR}" || exit 99 + +exit 0 diff -Nru opencryptoki-3.18.0+dfsg/testcases/unit/unit.mk opencryptoki-3.20.0+dfsg/testcases/unit/unit.mk --- opencryptoki-3.18.0+dfsg/testcases/unit/unit.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/testcases/unit/unit.mk 2023-02-13 09:22:42.000000000 +0100 @@ -1,8 +1,12 @@ check_PROGRAMS = testcases/unit/policytest testcases/unit/hashmaptest \ - testcases/unit/mechtabletest testcases/unit/configdump + testcases/unit/mechtabletest testcases/unit/configdump \ + testcases/unit/buffertest testcases/unit/uritest \ + testcases/unit/pintest TESTS = testcases/unit/policytest testcases/unit/hashmaptest \ - testcases/unit/mechtabletest testcases/unit/configdump + testcases/unit/mechtabletest testcases/unit/configdump \ + testcases/unit/buffertest testcases/unit/uritest \ + testcases/unit/pintest.sh testcases_unit_policytest_CFLAGS=-I${top_srcdir}/usr/lib/common \ -I${top_srcdir}/usr/lib/api -I${top_srcdir}/usr/include \ @@ -18,7 +22,8 @@ usr/lib/common/kdf_translation.c \ usr/lib/common/mgf_translation.c \ usr/lib/api/supportedstrengths.c \ - usr/lib/config/cfgparse.y usr/lib/config/cfglex.l + usr/lib/config/cfgparse.y usr/lib/config/cfglex.l \ + usr/lib/common/pqc_supported.c nodist_testcases_unit_policytest_SOURCES=usr/lib/api/mechtable.c @@ -42,3 +47,21 @@ testcases_unit_configdump_CFLAGS=-I${top_srcdir}/usr/lib/config \ -I${top_builddir}/usr/lib/config + +testcases_unit_buffertest_SOURCES=testcases/unit/buffertest.c \ + usr/lib/common/buffer.c + +testcases_unit_buffertest_CFLAGS=-I${top_srcdir}/usr/lib/common + +testcases_unit_uritest_SOURCES=testcases/unit/uritest.c \ + usr/lib/common/uri.c usr/lib/common/buffer.c \ + usr/lib/common/p11util.c + +testcases_unit_uritest_CFLAGS=-I${top_srcdir}/usr/lib/common \ + -I${top_srcdir}/usr/include -I${top_builddir}/usr/lib/api + +testcases_unit_pintest_SOURCES=testcases/unit/pintest.c \ + usr/lib/common/buffer.c usr/lib/common/pin_prompt.c + +testcases_unit_pintest_CFLAGS=-I${top_srcdir}/usr/lib/common +testcases_unit_pintest_LDFLAGS=-lcrypto diff -Nru opencryptoki-3.18.0+dfsg/testcases/unit/uritest.c opencryptoki-3.20.0+dfsg/testcases/unit/uritest.c --- opencryptoki-3.18.0+dfsg/testcases/unit/uritest.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/testcases/unit/uritest.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,421 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ +#include +#include +#include +#include + +#include +#include "unittest.h" + +#define BUFLEN 128 + +#define MIN(a, b) (a < b) ? (a) : (b) +#define BINIT(s, e) memset(s.e, ' ', sizeof(s.e)) +#define SCPY(s, e, c) _cpy(s.e, sizeof(s.e), c) + +static CK_INFO i; +static CK_SLOT_INFO s; +static CK_TOKEN_INFO t; + +static CK_OBJECT_CLASS cko_data = CKO_DATA; +static CK_OBJECT_CLASS cko_pubk = CKO_PUBLIC_KEY; +static CK_OBJECT_CLASS cko_cert = CKO_CERTIFICATE; +static CK_OBJECT_CLASS cko_prvk = CKO_PRIVATE_KEY; +static CK_OBJECT_CLASS cko_seck = CKO_SECRET_KEY; + +static CK_CHAR ckc_id_buf[BUFLEN]; +static CK_CHAR ckc_label_buf[BUFLEN]; + +static void _cpy(unsigned char *dest, size_t d_len, char *src) +{ + size_t s_len; + + if (!src) + return; + + s_len = strlen(src); + memcpy(dest, src, MIN(s_len, d_len)); +} + +static void _gen_uri(struct p11_uri *uri, + char *i_dsc, char *i_man, int i_vmj, int i_vmi, + int s_id, char *s_dsc, char *s_man, + char *t_lbl, char *t_man, char *t_mod, char *t_ser, + char *o_id, char *o_lbl, CK_OBJECT_CLASS_PTR o_type) +{ + /* initialize string fields */ + BINIT(i, manufacturerID); + BINIT(i, libraryDescription); + + BINIT(s, manufacturerID); + BINIT(s, slotDescription); + + BINIT(t, label); + BINIT(t, manufacturerID); + BINIT(t, model); + BINIT(t, serialNumber); + + /* initialize attribute templates */ + memset(ckc_id_buf, '\0', BUFLEN); + memset(ckc_label_buf, '\0', BUFLEN); + + /* info */ + SCPY(i, manufacturerID, i_man); + SCPY(i, libraryDescription, i_dsc); + i.libraryVersion.major = i_vmj; + i.libraryVersion.minor = i_vmi; + + /* slot */ + uri->slot_id = -1; + if (s_id >= 0) + uri->slot_id = s_id; + SCPY(s, manufacturerID, s_man); + SCPY(s, slotDescription, s_dsc); + + /* token */ + SCPY(t, label, t_lbl); + SCPY(t, manufacturerID, t_man); + SCPY(t, model, t_mod); + SCPY(t, serialNumber, t_ser); + + uri->info = NULL; + if (i_man || i_dsc) + uri->info = &i; + + uri->slot_info = NULL; + if (s_man || s_dsc) + uri->slot_info = &s; + + uri->token_info = NULL; + if (t_lbl || t_man || t_mod || t_ser) + uri->token_info = &t; + + if (o_type) { + uri->obj_class[0].type = CKA_CLASS; + uri->obj_class[0].pValue = o_type; + uri->obj_class[0].ulValueLen = sizeof(CK_OBJECT_CLASS); + } + if (o_id) { + memcpy(ckc_id_buf, o_id, strlen(o_id)); + uri->obj_id[0].type = CKA_ID; + uri->obj_id[0].pValue = ckc_id_buf; + uri->obj_id[0].ulValueLen = strlen(o_id); + } + if (o_lbl) { + memcpy(ckc_label_buf, o_lbl, strlen(o_lbl)); + uri->obj_label[0].type = CKA_LABEL; + uri->obj_label[0].pValue = ckc_label_buf; + uri->obj_label[0].ulValueLen = strlen(o_lbl); + } +} + +static void _alloc_attr(CK_ATTRIBUTE_PTR attr) +{ + attr->pValue = malloc(8); + if (!attr->pValue) + return; + attr->ulValueLen = 8; +} + +static void _alloc_attrs(struct p11_uri *uri) +{ + _alloc_attr(&uri->obj_id[0]); + _alloc_attr(&uri->obj_label[0]); + _alloc_attr(&uri->obj_class[0]); +} + +static int test_uri_base(void) +{ + int result = 0; + struct p11_uri *uri; + + uri = p11_uri_new(); + if (!uri) + return 1; + if ((uri == NULL) || + (uri->priv == NULL)) { + fprintf(stderr, "[%d] %s: %s\n", + 0, "p11_uri_new()", + "wrong initial uri values"); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + _alloc_attrs(uri); + p11_uri_attributes_free(uri); + if ((uri->obj_id[0].pValue) || (uri->obj_id[0].ulValueLen) || + (uri->obj_label[0].pValue) || (uri->obj_label[0].ulValueLen) || + (uri->obj_class[0].pValue) || (uri->obj_class[0].ulValueLen)) { + fprintf(stderr, "[%d] %s: %s\n", + 1, "p11_uri_attributes_free()", + "wrong uri attribute values after free"); + result++; + } + p11_uri_free(uri); + + return result; +} + +static int test_uri_format(void) +{ + int result = 0; + const char *cur_uri, *exp_uri; + struct p11_uri *uri; + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:library-description=testLib;library-manufacturer=ACME;library-version=47.11"; + _gen_uri(uri, + "testLib", "ACME", 47, 11, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + NULL, NULL, NULL); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 0, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:slot-id=0;slot-description=testslot;slot-manufacturer=ACME"; + _gen_uri(uri, + NULL, NULL, -1, -1, + 0, "testslot", "ACME", + NULL, NULL, NULL, NULL, + NULL, NULL, NULL); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 1, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:manufacturer=ACME;model=TestModel;serial=0123456789;token=testtok"; + _gen_uri(uri, + NULL, NULL, -1, -1, + -1, NULL, NULL, + "testtok", "ACME", "TestModel", "0123456789", + NULL, NULL, NULL); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 2, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:id=%30%31%32%33%34%35%36%37%38%39%61%62%63;object=testo_data;type=data"; + _gen_uri(uri, + NULL, NULL, -1, -1, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + "0123456789abc", "testo_data", &cko_data); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 3, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:id=%30%31%32%33%34%35%36%37%38%39%61%62%63;object=testo_privk;type=private"; + _gen_uri(uri, + NULL, NULL, -1, -1, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + "0123456789abc", "testo_privk", &cko_prvk); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 4, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:id=%30%31%32%33%34%35%36%37%38%39%61%62%63;object=testo_pubk;type=public"; + _gen_uri(uri, + NULL, NULL, -1, -1, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + "0123456789abc", "testo_pubk", &cko_pubk); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 5, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:id=%30%31%32%33%34%35%36%37%38%39%61%62%63;object=testo_seck;type=secret-key"; + _gen_uri(uri, + NULL, NULL, -1, -1, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + "0123456789abc", "testo_seck", &cko_seck); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 6, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:id=%30%31%32%33%34%35%36%37%38%39%61%62%63;object=testo_cert;type=cert"; + _gen_uri(uri, + NULL, NULL, -1, -1, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + "0123456789abc", "testo_cert", &cko_cert); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 7, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:"; + _gen_uri(uri, + NULL, NULL, -1, -1, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + NULL, NULL, NULL); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 8, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + return result; +} + +static int test_uri_encode(void) +{ + int result = 0; + const char *cur_uri, *exp_uri; + struct p11_uri *uri; + + /* common non-encode characters */ + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:library-description=abcdefghijklmnopqrstuvwxyz;library-manufacturer=ACME;library-version=47.11"; + _gen_uri(uri, + "abcdefghijklmnopqrstuvwxyz", "ACME", 47, 11, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + NULL, NULL, NULL); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 0, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:library-description=ABCDEFGHIJKLMNOPQRSTUVWXYZ;library-manufacturer=ACME;library-version=47.11"; + _gen_uri(uri, + "ABCDEFGHIJKLMNOPQRSTUVWXYZ", "ACME", 47, 11, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + NULL, NULL, NULL); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 1, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:library-description=0123456789_-.;library-manufacturer=ACME;library-version=47.11"; + _gen_uri(uri, + "0123456789_-.", "ACME", 47, 11, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + NULL, NULL, NULL); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 2, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + /* reserved non-encode characters */ + uri = p11_uri_new(); + if (!uri) + return 1; + exp_uri = "pkcs11:library-description=:[]@!$\'()*+,=;library-manufacturer=ACME;library-version=47.11"; + _gen_uri(uri, + ":[]@!$\'()*+,=", "ACME", 47, 11, + -1, NULL, NULL, + NULL, NULL, NULL, NULL, + NULL, NULL, NULL); + cur_uri = p11_uri_format(uri); + if (strcmp(cur_uri, exp_uri) != 0) { + fprintf(stderr,"[%d] p11_uri_format(): curr: %s, expected: %s\n", + 3, cur_uri, exp_uri); + result++; + } + p11_uri_free(uri); + + return result; +} + +int main(void) +{ + if (test_uri_base()) + return TEST_FAIL; + if (test_uri_format()) + return TEST_FAIL; + if (test_uri_encode()) + return TEST_FAIL; + + return TEST_PASS; +} diff -Nru opencryptoki-3.18.0+dfsg/tools/policyexamplegen.c opencryptoki-3.20.0+dfsg/tools/policyexamplegen.c --- opencryptoki-3.18.0+dfsg/tools/policyexamplegen.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/tools/policyexamplegen.c 2023-02-13 09:22:42.000000000 +0100 @@ -99,7 +99,13 @@ puts(" CKD_SHA224_KDF,"); puts(" CKD_SHA256_KDF,"); puts(" CKD_SHA384_KDF,"); - puts(" CKD_SHA512_KDF"); + puts(" CKD_SHA512_KDF,"); + puts(" CKD_IBM_HYBRID_NULL,"); + puts(" CKD_IBM_HYBRID_SHA1_KDF,"); + puts(" CKD_IBM_HYBRID_SHA224_KDF,"); + puts(" CKD_IBM_HYBRID_SHA256_KDF,"); + puts(" CKD_IBM_HYBRID_SHA384_KDF,"); + puts(" CKD_IBM_HYBRID_SHA512_KDF"); puts(" # No comma after last element!"); puts(")"); puts(""); diff -Nru opencryptoki-3.18.0+dfsg/tools/tableidxgen.c opencryptoki-3.20.0+dfsg/tools/tableidxgen.c --- opencryptoki-3.18.0+dfsg/tools/tableidxgen.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/tools/tableidxgen.c 2023-02-13 09:22:42.000000000 +0100 @@ -416,7 +416,7 @@ fputs("Jump table:\n", fp); for (n = root; n; n = n->nextnum) { - fprintf(fp, "node %hd: (offset %u)\n", n->num, n->offset); + fprintf(fp, "node %hu: (offset %u)\n", n->num, n->offset); for (i = 0; i < 256; ++i) { if (n->table[i] > 0) fprintf(fp, " %d (%d) => node %hd\n", i, (int)idxtable[i], diff -Nru opencryptoki-3.18.0+dfsg/tools/tools.mk opencryptoki-3.20.0+dfsg/tools/tools.mk --- opencryptoki-3.18.0+dfsg/tools/tools.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/tools/tools.mk 2023-02-13 09:22:42.000000000 +0100 @@ -1,7 +1,27 @@ noinst_PROGRAMS += tools/tableidxgen tools/policyexamplegen +TOOLS_CFLAGS = -I${srcdir}/usr/include -I${srcdir}/usr/lib/api -I${top_builddir}/usr/lib/api + tools_tableidxgen_SOURCES = tools/tableidxgen.c usr/lib/api/mechtable.inc -tools_tableidxgen_CFLAGS = -I${srcdir}/usr/include -I${srcdir}/usr/lib/api tools_policyexamplegen_SOURCES = tools/policyexamplegen.c usr/lib/api/mechtable.c -tools_policyexamplegen_CFLAGS = -I${srcdir}/usr/include -I${srcdir}/usr/lib/api -I${top_builddir}/usr/lib/api + +if CROSS +tools_tableidxgen_LINK = $(CC_FOR_BUILD) $(CFLAGS_FOR_BUILD) $(LDFLAGS_FOR_BUILD) -o $@ + +$(tools_tableidxgen_OBJECTS): CC=$(CC_FOR_BUILD) +$(tools_tableidxgen_OBJECTS): CFLAGS=$(CFLAGS_FOR_BUILD) $(TOOLS_CFLAGS) +$(tools_tableidxgen_OBJECTS): LDFLAGS=$(LDFLAGS_FOR_BUILD) + +tools_policyexamplegen_LINK = $(CC_FOR_BUILD) $(CFLAGS_FOR_BUILD) $(LDFLAGS_FOR_BUILD) -o $@ + +$(tools_policyexamplegen_OBJECTS): CC=$(CC_FOR_BUILD) +$(tools_policyexamplegen_OBJECTS): CFLAGS=$(CFLAGS_FOR_BUILD) $(TOOLS_CFLAGS) +$(tools_policyexamplegen_OBJECTS): LDFLAGS=$(LDFLAGS_FOR_BUILD) +else +tools_tableidxgen_LINK = $(LINK) +tools_tableidxgen_CFLAGS = $(TOOLS_CFLAGS) + +tools_policyexamplegen_LINK = $(LINK) +tools_policyexamplegen_CFLAGS = $(TOOLS_CFLAGS) +endif diff -Nru opencryptoki-3.18.0+dfsg/.travis.yml opencryptoki-3.20.0+dfsg/.travis.yml --- opencryptoki-3.18.0+dfsg/.travis.yml 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/.travis.yml 2023-02-13 09:22:42.000000000 +0100 @@ -5,7 +5,7 @@ before_install: - sudo apt-get -qq update - - sudo apt-get install -y expect libldap2-dev wget libudev-dev + - sudo apt-get install -y expect libldap2-dev wget libudev-dev autoconf-archive - if [ "$TRAVIS_CPU_ARCH" != "amd64" ]; then sudo apt-get install -y trousers libtspi-dev; fi - sudo wget https://launchpad.net/ubuntu/+archive/primary/+files/libica3_3.4.0-0ubuntu1_s390x.deb - sudo wget https://launchpad.net/ubuntu/+archive/primary/+files/libica-dev_3.4.0-0ubuntu1_s390x.deb @@ -18,48 +18,49 @@ - name: "linux-x86-clang-locks" os: linux compiler: clang - env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-testcases --enable-locks" CFLAGS="-O3 -Wextra -std=c99 -pedantic -Werror -DDEBUG" + env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-testcases --enable-locks --with-systemd" CFLAGS="-O3 -Werror -DDEBUG" - name: "linux-x86-gcc-tm" os: linux compiler: gcc - env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-testcases --disable-locks" CFLAGS="-O3 -Wno-clobbered -Wextra -std=c99 -pedantic -Werror" + env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-testcases --disable-locks --with-systemd" CFLAGS="-O3 -Wno-clobbered -Werror" - name: "linux-ppc64le-clang-locks" os: linux arch: ppc64le compiler: clang - env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-testcases --enable-locks" CFLAGS="-O3 -Wextra -std=c99 -pedantic -Werror" + env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-testcases --enable-locks --with-systemd" CFLAGS="-O3 -Werror" - name: "linux-ppc64le-gcc-tm" os: linux arch: ppc64le compiler: gcc - env: CONFIG_OPTS="--enable-swttok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-testcases --disable-locks" CFLAGS="-O3 -Wno-clobbered -Wextra -std=c99 -pedantic -Werror -DDEBUG" + env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-testcases --disable-locks --with-systemd" CFLAGS="-O3 -Wno-clobbered -Werror -DDEBUG" - name: "linux-s390x-clang-locks" os: linux arch: s390x compiler: clang - env: CONFIG_OPTS="--enable-swttok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-icatok --enable-ep11tok --enable-testcases --enable-locks" CFLAGS="-O3 -Wextra -std=c99 -pedantic -Werror -DDEBUG" + env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-icatok --enable-ep11tok --enable-testcases --enable-locks --with-systemd" CFLAGS="-O3 -Werror -DDEBUG" - name: "linux-s390x-gcc-tm" os: linux arch: s390x compiler: gcc - env: CONFIG_OPTS="--enable-swttok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-icatok --enable-ep11tok --enable-testcases --disable-locks" CFLAGS="-O3 -Wno-clobbered -Wextra -std=c99 -pedantic -Werror" + env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-icatok --enable-ep11tok --enable-testcases --disable-locks --with-systemd" CFLAGS="-O3 -Wno-clobbered -Werror" - name: "linux-arm64-clang-locks" os: linux arch: arm64 compiler: clang - env: CONFIG_OPTS="--enable-swttok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-testcases --enable-locks" CFLAGS="-O3 -Wextra -std=c99 -pedantic -Werror" + env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-testcases --enable-locks --with-systemd" CFLAGS="-O3 -Werror" - name: "linux-arm64-gcc-tm" os: linux arch: arm64 compiler: gcc - env: CONFIG_OPTS="--enable-swttok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-testcases --disable-locks" CFLAGS="-O3 -Wno-clobbered -Wextra -std=c99 -pedantic -Werror -DDEBUG" + env: CONFIG_OPTS="--enable-swtok --enable-icsftok --enable-ccatok --enable-tpmtok --enable-testcases --disable-locks --with-systemd" CFLAGS="-O3 -Wno-clobbered -Werror -DDEBUG" before_script: - sudo groupadd pkcs11 - ./bootstrap.sh script: - - ./configure $CONFIG_OPTS && make + - ./configure --silent $CONFIG_OPTS && make V=0 + - make check V=0 - sudo make install - sudo ldconfig - sudo pkcsslotd @@ -68,3 +69,4 @@ - sudo pkcsconf -t - cd testcases - sudo PKCS11_SO_PIN=76543210 PKCS11_USER_PIN=01234567 PKCSLIB=/usr/local/lib/pkcs11/libopencryptoki.so ./ock_tests.sh -s 3 + - sudo SLOT=3 PKCS11_USER_PIN=01234567 PKCSLIB=/usr/local/lib/pkcs11/libopencryptoki.so ./misc_tests/p11sak_test.sh diff -Nru opencryptoki-3.18.0+dfsg/usr/include/include.mk opencryptoki-3.20.0+dfsg/usr/include/include.mk --- opencryptoki-3.18.0+dfsg/usr/include/include.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/include/include.mk 2023-02-13 09:22:42.000000000 +0100 @@ -3,7 +3,7 @@ opencryptokiinclude_HEADERS = \ usr/include/apiclient.h usr/include/pkcs11types.h \ usr/include/pkcs11.h \ - usr/include/ec_curves.h + usr/include/ec_curves.h usr/include/pqc_oids.h noinst_HEADERS += \ usr/include/apictl.h usr/include/local_types.h \ diff -Nru opencryptoki-3.18.0+dfsg/usr/include/pkcs11types.h opencryptoki-3.20.0+dfsg/usr/include/pkcs11types.h --- opencryptoki-3.18.0+dfsg/usr/include/pkcs11types.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/include/pkcs11types.h 2023-02-13 09:22:42.000000000 +0100 @@ -431,12 +431,20 @@ #define CKK_CDMF 0x0000001E /* CKK_AES is new for v2.11 */ #define CKK_AES 0x0000001F +/* CKK_AES_XTS is new for v3.0 */ +#define CKK_AES_XTS 0x00000035 #define CKK_VENDOR_DEFINED 0x80000000 #ifndef OCK_NO_EP11_DEFINES #define CKK_IBM_PQC_DILITHIUM CKK_VENDOR_DEFINED + 0x10023 #endif +#define CKK_IBM_DILITHIUM CKK_IBM_PQC_DILITHIUM + +#ifndef OCK_NO_EP11_DEFINES +#define CKK_IBM_PQC_KYBER CKK_VENDOR_DEFINED + 0x10024 +#endif +#define CKK_IBM_KYBER CKK_IBM_PQC_KYBER /* CK_CERTIFICATE_TYPE is a value that identifies a certificate * type */ @@ -594,8 +602,15 @@ #define CKA_IBM_PROTKEY_NEVER_EXTRACTABLE (CKA_VENDOR_DEFINED +0x1000d) #define CKA_IBM_OPAQUE_PKEY (CKA_VENDOR_DEFINED + 0xd0100) -/* For Dilithium, oid = 1.3.6.1.4.1.2.267.1.6.5 */ -#define IBM_DILITHIUM_KEYFORM_ROUND2 1 +#define CK_IBM_DILITHIUM_KEYFORM_ROUND2_65 1 +#define CK_IBM_DILITHIUM_KEYFORM_ROUND2_87 2 +#define CK_IBM_DILITHIUM_KEYFORM_ROUND3_44 3 +#define CK_IBM_DILITHIUM_KEYFORM_ROUND3_65 4 +#define CK_IBM_DILITHIUM_KEYFORM_ROUND3_87 5 + +#define IBM_DILITHIUM_KEYFORM_ROUND2 CK_IBM_DILITHIUM_KEYFORM_ROUND2_65 + +#define CKA_IBM_DILITHIUM_MODE (CKA_VENDOR_DEFINED + 0x00010) #define CKA_IBM_DILITHIUM_KEYFORM (CKA_VENDOR_DEFINED + 0xd0001) #define CKA_IBM_DILITHIUM_RHO (CKA_VENDOR_DEFINED + 0xd0002) @@ -606,6 +621,49 @@ #define CKA_IBM_DILITHIUM_T0 (CKA_VENDOR_DEFINED + 0xd0007) #define CKA_IBM_DILITHIUM_T1 (CKA_VENDOR_DEFINED + 0xd0008) +#define CKA_IBM_KYBER_MODE (CKA_VENDOR_DEFINED + 0x0000E) + +#define CKA_IBM_KYBER_KEYFORM (CKA_VENDOR_DEFINED + 0xd0009) +#define CKA_IBM_KYBER_PK (CKA_VENDOR_DEFINED + 0xd000A) +#define CKA_IBM_KYBER_SK (CKA_VENDOR_DEFINED + 0xd000B) + +#define CK_IBM_KYBER_KEYFORM_ROUND2_768 1 +#define CK_IBM_KYBER_KEYFORM_ROUND2_1024 2 + +#define CK_IBM_KYBER_KEM_VERSION 0 + +typedef CK_ULONG CK_IBM_KYBER_KEM_MODE; + +#define CK_IBM_KYBER_KEM_ENCAPSULATE 1 +#define CK_IBM_KYBER_KEM_DECAPSULATE 2 + +typedef CK_ULONG CK_IBM_KYBER_KDF_TYPE; + +#if !defined(CKD_VENDOR_DEFINED) +#define CKD_VENDOR_DEFINED 0x80000000UL +#endif + +#ifndef OCK_NO_EP11_DEFINES +#define CKD_IBM_HYBRID_NULL CKD_VENDOR_DEFINED + 0x00000001UL +#define CKD_IBM_HYBRID_SHA1_KDF CKD_VENDOR_DEFINED + 0x00000002UL +#define CKD_IBM_HYBRID_SHA224_KDF CKD_VENDOR_DEFINED + 0x00000003UL +#define CKD_IBM_HYBRID_SHA256_KDF CKD_VENDOR_DEFINED + 0x00000004UL +#define CKD_IBM_HYBRID_SHA384_KDF CKD_VENDOR_DEFINED + 0x00000005UL +#define CKD_IBM_HYBRID_SHA512_KDF CKD_VENDOR_DEFINED + 0x00000006UL +#endif + +typedef struct CK_IBM_KYBER_PARAMS { + CK_ULONG ulVersion; + CK_IBM_KYBER_KEM_MODE mode; + CK_IBM_KYBER_KDF_TYPE kdf; + CK_BBOOL bPrepend; + CK_BYTE *pCipher; + CK_ULONG ulCipherLen; + CK_BYTE *pSharedData; + CK_ULONG ulSharedDataLen; + CK_OBJECT_HANDLE hSecret; +} CK_IBM_KYBER_PARAMS; + /* For NSS 3.30: */ #define NSSCK_VENDOR_NSS 0x4E534350 #define CKA_NSS (CKA_VENDOR_DEFINED | NSSCK_VENDOR_NSS) @@ -902,6 +960,9 @@ #define CKM_JUNIPER_SHUFFLE 0x00001064 #define CKM_JUNIPER_WRAP 0x00001065 #define CKM_FASTHASH 0x00001070 +/* The following are new for v3.0 */ +#define CKM_AES_XTS 0x00001071 +#define CKM_AES_XTS_KEY_GEN 0x00001072 /* The following are new for v2.11 */ #define CKM_AES_KEY_GEN 0x00001080 #define CKM_AES_ECB 0x00001081 @@ -933,6 +994,7 @@ #define CKM_IBM_SHA3_512 CKM_VENDOR_DEFINED + 0x00010004 #define CKM_IBM_CMAC CKM_VENDOR_DEFINED + 0x00010007 #define CKM_IBM_DILITHIUM CKM_VENDOR_DEFINED + 0x00010023 +#define CKM_IBM_KYBER CKM_VENDOR_DEFINED + 0x00010024 #define CKM_IBM_SHA3_224_HMAC CKM_VENDOR_DEFINED + 0x00010025 #define CKM_IBM_SHA3_256_HMAC CKM_VENDOR_DEFINED + 0x00010026 #define CKM_IBM_SHA3_384_HMAC CKM_VENDOR_DEFINED + 0x00010027 @@ -941,7 +1003,9 @@ #define CKM_IBM_ED25519_SHA512 CKM_VENDOR_DEFINED + 0x0001001c #define CKM_IBM_EC_X448 CKM_VENDOR_DEFINED + 0x0001001e #define CKM_IBM_ED448_SHA3 CKM_VENDOR_DEFINED + 0x0001001f +#define CKM_IBM_ECDSA_OTHER CKM_VENDOR_DEFINED + 0x00010031 #define CKM_IBM_ATTRIBUTEBOUND_WRAP CKM_VENDOR_DEFINED + 0x00020004 +#define CKM_IBM_BTC_DERIVE CKM_VENDOR_DEFINED + 0x00070001 #endif #define CKM_IBM_EC_C25519 CKM_IBM_EC_X25519 @@ -977,6 +1041,14 @@ * Bit Flag Mask Meaning */ #define CKF_HW 0x00000001 /* performed by HW */ +/* new for PKCS#11 v3.0 */ +#define CKF_MESSAGE_ENCRYPT 0x00000002 +#define CKF_MESSAGE_DECRYPT 0x00000004 +#define CKF_MESSAGE_SIGN 0x00000008 +#define CKF_MESSAGE_VERIFY 0x00000010 +#define CKF_MULTI_MESSAGE 0x00000020 +#define CKF_FIND_OBJECTS 0x00000040 + /* The flags CKF_ENCRYPT, CKF_DECRYPT, CKF_DIGEST, CKF_SIGN, * CKG_SIGN_RECOVER, CKF_VERIFY, CKF_VERIFY_RECOVER, * CKF_GENERATE, CKF_GENERATE_KEY_PAIR, CKF_WRAP, CKF_UNWRAP, @@ -1151,6 +1223,10 @@ /* CKR_FUNCTION_REJECTED is new for v2.20 */ #define CKR_FUNCTION_REJECTED 0x00000200 +/* New to v3.0 */ +#define CKR_TOKEN_RESOURCE_EXCEEDED 0x00000201 +#define CKR_OPERATION_CANCEL_FAILED 0x00000202 + #define CKR_VENDOR_DEFINED 0x80000000 /* Not really a return value, but stored in ulDeviceError of session info for policy violations. */ @@ -1287,6 +1363,7 @@ typedef struct CK_GCM_PARAMS { CK_BYTE_PTR pIv; CK_ULONG ulIvLen; + CK_ULONG ulIvBits; CK_BYTE_PTR pAAD; CK_ULONG ulAADLen; CK_ULONG ulTagBits; @@ -1294,6 +1371,24 @@ typedef CK_GCM_PARAMS CK_PTR CK_GCM_PARAMS_PTR; +/* + * There is a discrepancy between what the PKCS#11 v2.40 standard states in the + * documentation and the official header file about structure CK_GCM_PARAMS: + * https://docs.oasis-open.org/pkcs11/pkcs11-base/v2.40/errata01/os/include/pkcs11-v2.40/pkcs11t.h + * The header file defines field ulIvBits for structure CK_GCM_PARAMS, but the + * documentation does not mention that field at all. + * Opencryptoki accepts both versions of the CK_GCM_PARAMS structure, with or + * without the field. Structure CK_GCM_PARAMS_COMPAT represents the one without + * field ulIvBits. + */ +typedef struct CK_GCM_PARAMS_COMPAT { + CK_BYTE_PTR pIv; + CK_ULONG ulIvLen; + CK_BYTE_PTR pAAD; + CK_ULONG ulAADLen; + CK_ULONG ulTagBits; +} CK_GCM_PARAMS_COMPAT; + /* CK_RC5_CBC_PARAMS provides the parameters to the CKM_RC5_CBC * mechanism */ /* CK_RC5_CBC_PARAMS is new for v2.0 */ @@ -1526,6 +1621,47 @@ #define CKP_PKCS5_PBKD2_HMAC_SHA256 0x00000004UL #define CKP_PKCS5_PBKD2_HMAC_SHA512 0x00000006UL +#ifndef OCK_NO_EP11_DEFINES +/* For CKM_IBM_BTC_DERIVE */ +typedef struct CK_IBM_BTC_DERIVE_PARAMS { + CK_ULONG type; + CK_ULONG childKeyIndex; + CK_BYTE_PTR pChainCode; + CK_ULONG ulChainCodeLen; + CK_ULONG version; +} CK_IBM_BTC_DERIVE_PARAMS; + +typedef CK_IBM_BTC_DERIVE_PARAMS CK_PTR CK_IBM_BTC_DERIVE_PARAMS_PTR; +#endif + +#define CK_IBM_BTC_DERIVE_PARAMS_VERSION_1 1 + +/* Key index flag */ +#define CK_IBM_BTC_BIP0032_HARDENED 0x80000000 + +/* BTC types */ +#define CK_IBM_BTC_BIP0032_PRV2PRV 1 +#define CK_IBM_BTC_BIP0032_PRV2PUB 2 +#define CK_IBM_BTC_BIP0032_PUB2PUB 3 +#define CK_IBM_BTC_BIP0032_MASTERK 4 +#define CK_IBM_BTC_SLIP0010_PRV2PRV 5 +#define CK_IBM_BTC_SLIP0010_PRV2PUB 6 +#define CK_IBM_BTC_SLIP0010_PUB2PUB 7 +#define CK_IBM_BTC_SLIP0010_MASTERK 8 + +#define CK_IBM_BTC_CHAINCODE_LENGTH 32 + +/* For CKM_IBM_ECDSA_OTHER */ +typedef struct CK_IBM_ECDSA_OTHER_PARAMS { + CK_MECHANISM_TYPE submechanism; +} CK_IBM_ECDSA_OTHER_PARAMS; + +typedef CK_IBM_ECDSA_OTHER_PARAMS CK_PTR CK_IBM_ECDSA_OTHER_PARAMS_PTR; + +/* CKM_IBM_ECDSA_OTHER sub-mechanisms */ +#define CKM_IBM_ECSDSA_RAND 3 +#define CKM_IBM_ECSDSA_COMPR_MULTI 5 + #define CKF_INTERFACE_FORK_SAFE 0x00000001UL /* CK_INTERFACE is a structure which contains diff -Nru opencryptoki-3.18.0+dfsg/usr/include/pqc_oids.h opencryptoki-3.20.0+dfsg/usr/include/pqc_oids.h --- opencryptoki-3.18.0+dfsg/usr/include/pqc_oids.h 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/include/pqc_oids.h 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,48 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + + +#ifndef _PQC_OIDS_H_ +#define _PQC_OIDS_H_ + +/* + * OIDs and their DER encoding for the post-quantum crypto algorithms + * supported by OpenCryptoki: + */ + +/* Dilithium Round 2 high-security (SHAKE-256): 1.3.6.1.4.1.2.267.1.6.5 */ +#define OCK_DILITHIUM_R2_65 { 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, \ + 0x01, 0x02, 0x82, 0x0B, 0x01, 0x06, 0x05 } + +/* Dilithium Round 2 for outbound authentication: 1.3.6.1.4.1.2.267.1.8.7 */ +#define OCK_DILITHIUM_R2_87 { 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, \ + 0x01, 0x02, 0x82, 0x0B, 0x01, 0x08, 0x07 } + +/* Dilithium Round 3 weak (SHAKE-256): 1.3.6.1.4.1.2.267.7.4.4 */ +#define OCK_DILITHIUM_R3_44 { 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, \ + 0x01, 0x02, 0x82, 0x0B, 0x07, 0x04, 0x04 } + +/* Dilithium Round 3 recommended (SHAKE-256): 1.3.6.1.4.1.2.267.7.6.5 */ +#define OCK_DILITHIUM_R3_65 { 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, \ + 0x01, 0x02, 0x82, 0x0B, 0x07, 0x06, 0x05 } + +/* Dilithium Round 3 high-security (SHAKE-256): 1.3.6.1.4.1.2.267.7.8.7 */ +#define OCK_DILITHIUM_R3_87 { 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, \ + 0x01, 0x02, 0x82, 0x0B, 0x07, 0x08, 0x07 } + +/* Kyber Round 2 768 (SHAKE-128): 1.3.6.1.4.1.2.267.5.3.3 */ +#define OCK_KYBER_R2_768 { 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, \ + 0x01, 0x02, 0x82, 0x0B, 0x05, 0x03, 0x03 } + +/* Kyber Round 2 1024 (SHAKE-128): 1.3.6.1.4.1.2.267.5.4.4 */ +#define OCK_KYBER_R2_1024 { 0x06, 0x0B, 0x2B, 0x06, 0x01, 0x04, \ + 0x01, 0x02, 0x82, 0x0B, 0x05, 0x04, 0x04 } + +#endif // _PQC_OIDS_H_ diff -Nru opencryptoki-3.18.0+dfsg/usr/include/slotmgr.h opencryptoki-3.20.0+dfsg/usr/include/slotmgr.h --- opencryptoki-3.18.0+dfsg/usr/include/slotmgr.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/include/slotmgr.h 2023-02-13 09:22:42.000000000 +0100 @@ -169,11 +169,12 @@ * sleeping on the condition variable to wakeup. */ uint32 slot_session_count[NUMBER_SLOTS_MANAGED]; /* Per process session - * count for garbage + * counts for garbage * collection clean up * of the global * session count. */ + uint32 slot_rw_session_count[NUMBER_SLOTS_MANAGED]; time_t_64 reg_time; // Time application registered } Slot_Mgr_Proc_t_64; @@ -201,6 +202,7 @@ /* Information that the API calls will use. */ uint32 slot_global_sessions[NUMBER_SLOTS_MANAGED]; + uint32 slot_global_rw_sessions[NUMBER_SLOTS_MANAGED]; Slot_Mgr_Proc_t_64 proc_table[NUMBER_PROCESSES_ALLOWED]; } Slot_Mgr_Shr_t; diff -Nru opencryptoki-3.18.0+dfsg/usr/include/stdll.h opencryptoki-3.20.0+dfsg/usr/include/stdll.h --- opencryptoki-3.18.0+dfsg/usr/include/stdll.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/include/stdll.h 2023-02-13 09:22:42.000000000 +0100 @@ -29,6 +29,7 @@ struct bt_ref_hdr hdr; CK_SLOT_ID slotID; CK_SESSION_HANDLE sessionh; + CK_BBOOL rw_session; } ST_SESSION_T; typedef struct trace_handle_t trace_handle; @@ -338,6 +339,9 @@ CK_FLAGS flags, CK_SLOT_ID_PTR pSlot, CK_VOID_PTR pReserved); +typedef CK_RV (CK_PTR ST_C_SessionCancel)(STDLL_TokData_t *tokdata, + ST_SESSION_T *hSession, + CK_FLAGS flags); typedef CK_RV (CK_PTR ST_C_IBM_ReencryptSingle)(STDLL_TokData_t *tokdata, ST_SESSION_T *hSession, @@ -427,6 +431,7 @@ // Question if these have to be implemented for Netscape support ST_C_GetFunctionStatus ST_GetFunctionStatus; ST_C_CancelFunction ST_CancelFunction; + ST_C_SessionCancel ST_SessionCancel; ST_C_IBM_ReencryptSingle ST_IBM_ReencryptSingle; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/api_interface.c opencryptoki-3.20.0+dfsg/usr/lib/api/api_interface.c --- opencryptoki-3.18.0+dfsg/usr/lib/api/api_interface.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/api_interface.c 2023-02-13 09:22:42.000000000 +0100 @@ -39,7 +39,16 @@ #include -void api_init(); +void api_init(void); + +static int openssl_err_cb(const char *str, size_t len, void *u) +{ + UNUSED(len); + UNUSED(u); + + TRACE_DEVEL("OpenSSL error: %s", str); + return 1; +} #if OPENSSL_VERSION_PREREQ(3, 0) #define BEGIN_OPENSSL_LIBCTX(ossl_ctx, rc) \ @@ -59,6 +68,7 @@ (rc) = CKR_FUNCTION_FAILED; \ TRACE_ERROR("OSSL_LIB_CTX_set0_default failed\n"); \ } \ + ERR_print_errors_cb(openssl_err_cb, NULL); \ ERR_pop_to_mark(); \ } while (0); #else @@ -67,6 +77,7 @@ ERR_set_mark(); #define END_OPENSSL_LIBCTX(rc) \ + ERR_print_errors_cb(openssl_err_cb, NULL); \ ERR_pop_to_mark(); \ } while (0); #endif @@ -296,7 +307,7 @@ } }; -void child_fork_initializer() +void child_fork_initializer(void) { /* * Reinitialize trace so that the trace output appears under the new @@ -325,7 +336,7 @@ in_child_fork_initializer = FALSE; } -void parent_fork_prepare() +void parent_fork_prepare(void) { if (Anchor == NULL) return; @@ -339,7 +350,7 @@ stop_event_thread(); } -void parent_fork_after() +void parent_fork_after(void) { if (Anchor == NULL) return; @@ -350,7 +361,7 @@ start_event_thread(); } -static CK_RV check_user_and_group() +static CK_RV check_user_and_group(void) { int i; uid_t euid; @@ -510,7 +521,7 @@ // proper tracking of the number of sessions on a slot. // This allows things like InitToken to properly work in case // other applications have the token active. - decr_sess_counts(rSession.slotID); + decr_sess_counts(rSession.slotID, rSession.rw_session); } else { TRACE_DEVEL("fcn->ST_CloseSession failed:0x%lx\n", rv); } @@ -2837,7 +2848,8 @@ BEGIN_OPENSSL_LIBCTX(Anchor->openssl_libctx, rv) rv = fcn->ST_GetTokenInfo(sltp->TokData, slotID, pInfo); if (rv == CKR_OK) { - get_sess_count(slotID, &(pInfo->ulSessionCount)); + get_sess_counts(slotID, &pInfo->ulSessionCount, + &pInfo->ulRwSessionCount); } TRACE_DEVEL("rv %lu CK_TOKEN_INFO Flags %lx\n", rv, pInfo->flags); END_OPENSSL_LIBCTX(rv) @@ -2849,7 +2861,7 @@ return rv; } // end of C_GetTokenInfo -void Call_Finalize() +void Call_Finalize(void) { C_Finalize(NULL); return; @@ -3539,6 +3551,7 @@ goto done; } apiSessp->slotID = slotID; + apiSessp->rw_session = (flags & CKF_RW_SESSION); // NOTE: Need to add Session counter to the shared // memory slot value.... Atomic operation. @@ -3548,7 +3561,7 @@ // how many sessions this process owns of the total amount. This // way if the process abends garbage collection in the slot manager // can adequatly clean up the total count value... - incr_sess_counts(slotID); + incr_sess_counts(slotID, apiSessp->rw_session); } else { free(apiSessp); @@ -4862,21 +4875,43 @@ CK_RV C_SessionCancel(CK_SESSION_HANDLE hSession, CK_FLAGS flags) { CK_RV rv; - - UNUSED(hSession); - UNUSED(flags); + API_Slot_t *sltp; + STDLL_FcnList_t *fcn; + ST_SESSION_T rSession; TRACE_INFO("C_SessionCancel\n"); if (API_Initialized() == FALSE) { TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - rv = CKR_CRYPTOKI_NOT_INITIALIZED; - goto ret; + return CKR_CRYPTOKI_NOT_INITIALIZED; + } + + if (!Valid_Session(hSession, &rSession)) { + TRACE_ERROR("%s\n", ock_err(ERR_SESSION_HANDLE_INVALID)); + TRACE_ERROR("Session handle id: %lu\n", hSession); + return CKR_SESSION_HANDLE_INVALID; + } + TRACE_INFO("Valid Session handle id: %lu\n", rSession.sessionh); + + sltp = &(Anchor->SltList[rSession.slotID]); + if (sltp->DLLoaded == FALSE) { + TRACE_ERROR("%s\n", ock_err(ERR_TOKEN_NOT_PRESENT)); + return CKR_TOKEN_NOT_PRESENT; + } + if ((fcn = sltp->FcnList) == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_TOKEN_NOT_PRESENT)); + return CKR_TOKEN_NOT_PRESENT; + } + if (fcn->ST_SessionCancel) { + BEGIN_OPENSSL_LIBCTX(Anchor->openssl_libctx, rv) + // Map the Session to the slot session + rv = fcn->ST_SessionCancel(sltp->TokData, &rSession, flags); + END_OPENSSL_LIBCTX(rv) + } else { + TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rv = CKR_FUNCTION_NOT_SUPPORTED; } - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); - rv = CKR_FUNCTION_NOT_SUPPORTED; -ret: return rv; } @@ -5480,7 +5515,7 @@ void api_fini(void) __attribute__ ((destructor)); #endif -void api_fini() +void api_fini(void) { if (API_Initialized() == TRUE) { in_destructor = TRUE; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/api.mk opencryptoki-3.20.0+dfsg/usr/lib/api/api.mk --- opencryptoki-3.18.0+dfsg/usr/lib/api/api.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/api.mk 2023-02-13 09:22:42.000000000 +0100 @@ -30,6 +30,7 @@ usr/lib/common/kdf_translation.c \ usr/lib/common/mgf_translation.c \ usr/lib/api/supportedstrengths.c \ + usr/lib/common/pqc_supported.c \ usr/lib/config/cfgparse.y usr/lib/config/cfglex.l nodist_opencryptoki_libopencryptoki_la_SOURCES = \ @@ -50,3 +51,5 @@ BUILT_SOURCES += usr/lib/api/mechtable-gen.h EXTRA_DIST += usr/lib/api/mechtable.inc +CLEANFILES += usr/lib/api/shrd_mem.c usr/lib/api/mechtable.c $(BUILT_SOURCES) \ + usr/lib/api/mechtable.log diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/apiproto.h opencryptoki-3.20.0+dfsg/usr/lib/api/apiproto.h --- opencryptoki-3.18.0+dfsg/usr/lib/api/apiproto.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/apiproto.h 2023-02-13 09:22:42.000000000 +0100 @@ -22,26 +22,26 @@ #include "policy.h" #include "statistics.h" -void *attach_shared_memory(); +void *attach_shared_memory(void); void detach_shared_memory(char *); -int API_Initialized(); -int API_Register(); -void API_UnRegister(); +int API_Initialized(void); +int API_Register(void); +void API_UnRegister(void); int DL_Load_and_Init(API_Slot_t *, CK_SLOT_ID, policy_t policy, statistics_t statistics); -CK_RV CreateProcLock(); +CK_RV CreateProcLock(void); CK_RV ProcLock(void); CK_RV ProcUnLock(void); CK_RV ProcClose(void); void _init(void); -void get_sess_count(CK_SLOT_ID, CK_ULONG *); -void incr_sess_counts(CK_SLOT_ID); -void decr_sess_counts(CK_SLOT_ID); +void get_sess_counts(CK_SLOT_ID, CK_ULONG *, CK_ULONG *); +void incr_sess_counts(CK_SLOT_ID, CK_BBOOL rw_session); +void decr_sess_counts(CK_SLOT_ID, CK_BBOOL rw_session); unsigned long AddToSessionList(ST_SESSION_T *); void RemoveFromSessionList(CK_SESSION_HANDLE); int Valid_Session(CK_SESSION_HANDLE, ST_SESSION_T *); @@ -55,7 +55,7 @@ void CloseAllSessions(CK_SLOT_ID slot_id, CK_BBOOL in_fork_initializer); int connect_socket(const char *file_path); int init_socket_data(int socketfd); -int start_event_thread(); -int stop_event_thread(); +int start_event_thread(void); +int stop_event_thread(void); #endif diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/apiutil.c opencryptoki-3.20.0+dfsg/usr/lib/api/apiutil.c --- opencryptoki-3.18.0+dfsg/usr/lib/api/apiutil.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/apiutil.c 2023-02-13 09:22:42.000000000 +0100 @@ -156,7 +156,7 @@ rv = fcn->ST_CloseSession(sltp->TokData, s, closeme_arg->in_fork_initializer); if (rv == CKR_OK) { - decr_sess_counts(closeme_arg->slot_id); + decr_sess_counts(closeme_arg->slot_id, s->rw_session); bt_node_free(&(Anchor->sess_btree), node_handle, TRUE); } } @@ -192,6 +192,7 @@ if (tmp) { rSession->slotID = tmp->slotID; rSession->sessionh = tmp->sessionh; + rSession->rw_session = tmp->rw_session; } rc = tmp ? TRUE : FALSE; bt_put_node_value(&(Anchor->sess_btree), tmp); @@ -200,7 +201,7 @@ return rc; } -int API_Initialized() +int API_Initialized(void) { if (Anchor == NULL) return FALSE; @@ -225,17 +226,18 @@ return TRUE; } -void get_sess_count(CK_SLOT_ID slotID, CK_ULONG *ret) +void get_sess_counts(CK_SLOT_ID slotID, CK_ULONG *ret, CK_ULONG *rw_ret) { Slot_Mgr_Shr_t *shm; shm = Anchor->SharedMemP; ProcLock(); *ret = shm->slot_global_sessions[slotID]; + *rw_ret = shm->slot_global_rw_sessions[slotID]; ProcUnLock(); } -void incr_sess_counts(CK_SLOT_ID slotID) +void incr_sess_counts(CK_SLOT_ID slotID, CK_BBOOL rw_session) { Slot_Mgr_Shr_t *shm; #ifdef PKCS64 @@ -250,14 +252,18 @@ ProcLock(); shm->slot_global_sessions[slotID]++; + if (rw_session) + shm->slot_global_rw_sessions[slotID]++; procp = &shm->proc_table[Anchor->MgrProcIndex]; procp->slot_session_count[slotID]++; + if (rw_session) + procp->slot_rw_session_count[slotID]++; ProcUnLock(); } -void decr_sess_counts(CK_SLOT_ID slotID) +void decr_sess_counts(CK_SLOT_ID slotID, CK_BBOOL rw_session) { Slot_Mgr_Shr_t *shm; #ifdef PKCS64 @@ -274,10 +280,16 @@ if (shm->slot_global_sessions[slotID] > 0) { shm->slot_global_sessions[slotID]--; } + if (rw_session && shm->slot_global_rw_sessions[slotID] > 0) { + shm->slot_global_rw_sessions[slotID]--; + } procp = &shm->proc_table[Anchor->MgrProcIndex]; if (procp->slot_session_count[slotID] > 0) { - procp->slot_session_count[slotID]++; + procp->slot_session_count[slotID]--; + } + if (rw_session && procp->slot_rw_session_count[slotID] > 0) { + procp->slot_rw_session_count[slotID]--; } ProcUnLock(); @@ -309,7 +321,7 @@ // This call must be made with the API Global Mutex Locked // and the Anchor control block initialized with the // shared memory. No checking for shared memory validity is done -int API_Register() +int API_Register(void) { long int reuse = -1, free = -1; Slot_Mgr_Shr_t *shm; @@ -404,7 +416,7 @@ // This call must be made with the API Global Mutex Locked // and the Anchor control block initialized with the // shared memory. No checking for shared memory validity is done -void API_UnRegister() +void API_UnRegister(void) { Slot_Mgr_Shr_t *shm; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/hashmap.c opencryptoki-3.20.0+dfsg/usr/lib/api/hashmap.c --- opencryptoki-3.18.0+dfsg/usr/lib/api/hashmap.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/hashmap.c 2023-02-13 09:22:42.000000000 +0100 @@ -78,7 +78,7 @@ /* Create size-optimized empty hash. First add will expand the hash to its * default capacity. */ -struct hashmap *hashmap_new() +struct hashmap *hashmap_new(void) { struct hashmap *res = malloc(sizeof(struct hashmap)); if (!res) diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/mechtable.inc opencryptoki-3.20.0+dfsg/usr/lib/api/mechtable.inc --- opencryptoki-3.18.0+dfsg/usr/lib/api/mechtable.inc 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/mechtable.inc 2023-02-13 09:22:42.000000000 +0100 @@ -40,6 +40,8 @@ { "CKM_AES_ECB", CKM_AES_ECB, 16, MC_INFORMATION_UNAVAILABLE, MCF_ENCRYPTDECRYPT | MCF_WRAPUNWRAP }, { "CKM_AES_GCM", CKM_AES_GCM, 16, MC_INFORMATION_UNAVAILABLE, MCF_ENCRYPTDECRYPT | MCF_WRAPUNWRAP | MCF_NEEDSPARAM }, { "CKM_AES_KEY_GEN", CKM_AES_KEY_GEN, 0, MC_INFORMATION_UNAVAILABLE, MCF_KEYGEN }, + { "CKM_AES_XTS_KEY_GEN", CKM_AES_XTS_KEY_GEN, 0, MC_INFORMATION_UNAVAILABLE, MCF_KEYGEN }, + { "CKM_AES_XTS", CKM_AES_XTS, 16, MC_INFORMATION_UNAVAILABLE, MCF_ENCRYPTDECRYPT }, { "CKM_AES_MAC", CKM_AES_MAC, 16, 8, MCF_SIGNVERIFY }, { "CKM_AES_MAC_GENERAL", CKM_AES_MAC_GENERAL, 16, 16, MCF_SIGNVERIFY | MCF_NEEDSPARAM | MCF_MAC_GENERAL }, { "CKM_AES_OFB", CKM_AES_OFB, 16, MC_INFORMATION_UNAVAILABLE, MCF_ENCRYPTDECRYPT | MCF_WRAPUNWRAP | MCF_NEEDSPARAM }, @@ -76,12 +78,15 @@ { "CKM_EC_KEY_PAIR_GEN", CKM_EC_KEY_PAIR_GEN, 0, MC_INFORMATION_UNAVAILABLE, MCF_KEYGEN }, { "CKM_GENERIC_SECRET_KEY_GEN", CKM_GENERIC_SECRET_KEY_GEN, 0, MC_INFORMATION_UNAVAILABLE, MCF_KEYGEN }, { "CKM_IBM_ATTRIBUTEBOUND_WRAP", CKM_IBM_ATTRIBUTEBOUND_WRAP, 0, MC_INFORMATION_UNAVAILABLE, MCF_WRAPUNWRAP | MCF_NEEDSPARAM }, + { "CKM_IBM_BTC_DERIVE", CKM_IBM_BTC_DERIVE, 0, MC_INFORMATION_UNAVAILABLE, MCF_DERIVE | MCF_NEEDSPARAM }, { "CKM_IBM_CMAC", CKM_IBM_CMAC, 0, MC_KEY_DEPENDENT, MCF_SIGNVERIFY }, - { "CKM_IBM_DILITHIUM", CKM_IBM_DILITHIUM, 0, 3366, MCF_SIGNVERIFY },/* Size unknown */ + { "CKM_IBM_DILITHIUM", CKM_IBM_DILITHIUM, 0, MC_KEY_DEPENDENT, MCF_KEYGEN | MCF_SIGNVERIFY }, + { "CKM_IBM_ECDSA_OTHER", CKM_IBM_ECDSA_OTHER, 0, MC_KEY_DEPENDENT, MCF_SIGNVERIFY | MCF_NEEDSPARAM }, { "CKM_IBM_EC_X25519", CKM_IBM_EC_X25519, 0, MC_INFORMATION_UNAVAILABLE, MCF_DERIVE }, { "CKM_IBM_EC_X448", CKM_IBM_EC_X448, 0, MC_INFORMATION_UNAVAILABLE, MCF_DERIVE }, { "CKM_IBM_ED25519_SHA512", CKM_IBM_ED25519_SHA512, 128, MC_KEY_DEPENDENT, MCF_SIGNVERIFY }, { "CKM_IBM_ED448_SHA3", CKM_IBM_ED448_SHA3, 144, MC_KEY_DEPENDENT, MCF_SIGNVERIFY }, + { "CKM_IBM_KYBER", CKM_IBM_KYBER, 0, MC_KEY_DEPENDENT, MCF_KEYGEN | MCF_ENCRYPTDECRYPT | MCF_DERIVE | MCF_NEEDSPARAM}, { "CKM_IBM_SHA3_224", CKM_IBM_SHA3_224, 144, 24, MCF_DIGEST }, { "CKM_IBM_SHA3_224_HMAC", CKM_IBM_SHA3_224_HMAC, 144, 24, MCF_SIGNVERIFY }, { "CKM_IBM_SHA3_256", CKM_IBM_SHA3_256, 136, 32, MCF_DIGEST }, @@ -142,9 +147,10 @@ { "CKM_SSL3_KEY_AND_MAC_DERIVE", CKM_SSL3_KEY_AND_MAC_DERIVE, 0, MC_INFORMATION_UNAVAILABLE, MCF_DERIVE | MCF_NEEDSPARAM }, { "CKM_SSL3_MASTER_KEY_DERIVE", CKM_SSL3_MASTER_KEY_DERIVE, 0, 48, MCF_DERIVE | MCF_NEEDSPARAM }, { "CKM_SSL3_MD5_MAC", CKM_SSL3_MD5_MAC, 64, 8, MCF_SIGNVERIFY | MCF_NEEDSPARAM }, - { "CKM_SSL3_PRE_MASTER_KEY_GEN", CKM_SSL3_PRE_MASTER_KEY_GEN, 0, 48, MCF_DERIVE | MCF_NEEDSPARAM }, + { "CKM_SSL3_PRE_MASTER_KEY_GEN", CKM_SSL3_PRE_MASTER_KEY_GEN, 0, 48, MCF_KEYGEN | MCF_NEEDSPARAM }, { "CKM_SSL3_SHA1_MAC", CKM_SSL3_SHA1_MAC, 64, 8, MCF_SIGNVERIFY | MCF_NEEDSPARAM }, { "CKM_TLS_KEY_AND_MAC_DERIVE", CKM_TLS_KEY_AND_MAC_DERIVE, 0, MC_INFORMATION_UNAVAILABLE, MCF_DERIVE | MCF_NEEDSPARAM }, + { "CKM_TLS_PRE_MASTER_KEY_GEN", CKM_TLS_PRE_MASTER_KEY_GEN, 0, 48, MCF_KEYGEN | MCF_NEEDSPARAM }, /* Not supported by any token, but needed for Token Store */ { "CKM_AES_KEY_WRAP", CKM_AES_KEY_WRAP, 16, MC_INFORMATION_UNAVAILABLE, MCF_ENCRYPTDECRYPT | MCF_WRAPUNWRAP | MCF_OPTIONALPARAM }, { "CKM_PKCS5_PBKD2", CKM_PKCS5_PBKD2, 0, MC_INFORMATION_UNAVAILABLE, MCF_KEYGEN | MCF_NEEDSPARAM }, diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/policy.c opencryptoki-3.20.0+dfsg/usr/lib/api/policy.c --- opencryptoki-3.18.0+dfsg/usr/lib/api/policy.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/policy.c 2023-02-13 09:22:42.000000000 +0100 @@ -25,6 +25,7 @@ #include #include #include +#include /* in h_extern.h, but not included since it creates too many unneeded dependencies for unit tests. */ @@ -69,6 +70,7 @@ CK_ULONG allowedmgfs; CK_ULONG allowedvendormgfs; CK_ULONG allowedkdfs; + CK_ULONG allowedvendorkdfs; CK_ULONG allowedprfs; CK_ULONG maxcurvesize; /* Strength struct ordered from highest to lowest. */ @@ -104,6 +106,7 @@ pp->allowedmgfs = ~0lu; pp->allowedvendormgfs = ~0lu; pp->allowedkdfs = ~0lu; + pp->allowedvendorkdfs = ~0lu; pp->allowedprfs = ~0lu; pp->maxcurvesize = 521u; } @@ -179,6 +182,65 @@ return rv; } +static CK_RV policy_get_pqc_args(CK_KEY_TYPE key_type, + get_attr_val_f getattr, void *d, + free_attr_f free_attr, CK_ULONG *size, + CK_ULONG *siglen, const CK_BYTE **oid, + CK_ULONG *oidlen) +{ + CK_ATTRIBUTE_TYPE keyform_attr; + CK_ATTRIBUTE_TYPE mode_attr; + CK_ATTRIBUTE *keyform = NULL, *mode = NULL; + const struct pqc_oid *oids, *pqc_oid = NULL; + CK_RV rv; + + switch (key_type) { + case CKK_IBM_PQC_DILITHIUM: + keyform_attr = CKA_IBM_DILITHIUM_KEYFORM; + mode_attr = CKA_IBM_DILITHIUM_MODE; + oids = dilithium_oids; + break; + case CKK_IBM_PQC_KYBER: + keyform_attr = CKA_IBM_KYBER_KEYFORM; + mode_attr = CKA_IBM_KYBER_MODE; + oids = kyber_oids; + break; + default: + TRACE_ERROR("Unsupported key type 0x%lx\n", key_type); + return CKR_KEY_TYPE_INCONSISTENT; + } + + rv = getattr(d, keyform_attr, &keyform); + if (rv == CKR_OK && keyform->ulValueLen == sizeof(CK_ULONG)) { + pqc_oid = find_pqc_by_keyform(oids, *(CK_ULONG *)keyform->pValue); + } else { + rv = getattr(d, mode_attr, &mode); + if (rv == CKR_OK && mode->ulValueLen > 0) + pqc_oid = find_pqc_by_oid(oids, mode->pValue, mode->ulValueLen); + } + if (pqc_oid == NULL) { + TRACE_ERROR("Did not find KEYFORM or MODE for key type 0x%lx\n", + key_type); + rv = CKR_TEMPLATE_INCOMPLETE; + goto out; + } + + *size = pqc_oid->policy_size; + *siglen = pqc_oid->policy_siglen; + *oid = pqc_oid->oid; + *oidlen = pqc_oid->oid_len; + +out: + if (free_attr) { + if (keyform) + free_attr(keyform); + if (mode) + free_attr(mode); + } + + return rv; +} + static CK_RV policy_extract_key_data(get_attr_val_f getattr, void *d, free_attr_f free_attr, CK_ULONG *comptarget, CK_ULONG *size, @@ -254,8 +316,11 @@ *siglen = 64; *comptarget = COMPARE_SYMMETRIC; break; + case CKK_AES_XTS: + /* Fallthrough */ case CKK_AES: - *siglen = 128; + if (*(CK_ULONG *)keytype->pValue == CKK_AES) + *siglen = 128; /* Fallthrough */ case CKK_GENERIC_SECRET: rv = getattr(d, CKA_VALUE_LEN, &keysize); @@ -270,10 +335,14 @@ goto out; } *size = (*(CK_ULONG*)keysize->pValue) * 8; + if (*(CK_ULONG *)keytype->pValue == CKK_AES_XTS) + *size /= 2; *comptarget = COMPARE_SYMMETRIC; break; case CKK_IBM_PQC_DILITHIUM: - *size = 256; + case CKK_IBM_PQC_KYBER: + rv = policy_get_pqc_args(*(CK_ULONG *)keytype->pValue, getattr, d, + free_attr, size, siglen, oid, oidlen); *comptarget = COMPARE_PQC; break; /* POLICY: New CKK */ @@ -315,7 +384,7 @@ const struct mechrow *col = mechrow_from_numeric(mech->mechanism); CK_ULONG size; - if (!col) + if (!col || !s) return CKR_FUNCTION_FAILED; if (col->flags & MCF_MAC_GENERAL) { if (mech->ulParameterLen != sizeof(CK_MAC_GENERAL_PARAMS)) { @@ -346,6 +415,8 @@ case CKM_RSA_X9_31: /* Fallthrough */ case CKM_IBM_ED448_SHA3: + /* Fallthrough */ + case CKM_IBM_DILITHIUM: *ssize = s->siglen; break; case CKM_DSA_SHA1: @@ -392,6 +463,17 @@ case CKM_IBM_ED25519_SHA512: *ssize = MIN(s->siglen, 512); break; + case CKM_IBM_ECDSA_OTHER: + switch (((CK_IBM_ECDSA_OTHER_PARAMS *) + mech->pParameter)->submechanism) { + case CKM_IBM_ECSDSA_RAND: + case CKM_IBM_ECSDSA_COMPR_MULTI: + *ssize = MIN(s->siglen, 256); /* Uses SHA-256 internally */ + break; + default: + return CKR_FUNCTION_FAILED; + } + break; default: return CKR_FUNCTION_FAILED; } @@ -407,10 +489,11 @@ CK_RSA_PKCS_MGF_TYPE mgf) { if (mgf > CKG_VENDOR_DEFINED) { - if (pp->allowedvendormgfs & (1u << (mgf - CKG_VENDOR_DEFINED - 1))) + if ((mgf - CKG_VENDOR_DEFINED - 1) <= 31 && + (pp->allowedvendormgfs & (1u << (mgf - CKG_VENDOR_DEFINED - 1)))) return CKR_OK; } else { - if (pp->allowedmgfs & (1u << mgf)) + if (mgf <= 31 && (pp->allowedmgfs & (1u << mgf))) return CKR_OK; } TRACE_WARNING("POLICY VIOLATION: mgf not allowed: 0x%lx\n", mgf); @@ -420,8 +503,14 @@ static inline CK_RV policy_is_kdf_allowed(struct policy_private *pp, CK_ULONG kdf) { - if (pp->allowedkdfs & (1u << kdf)) - return CKR_OK; + if (kdf > CKD_VENDOR_DEFINED) { + if ((kdf - CKD_VENDOR_DEFINED - 1) <= 31 && + (pp->allowedvendorkdfs & (1u << (kdf - CKD_VENDOR_DEFINED - 1)))) + return CKR_OK; + } else { + if (kdf <= 31 && (pp->allowedkdfs & (1u << kdf))) + return CKR_OK; + } TRACE_WARNING("POLICY VIOLATION: kdf not allowed: 0x%lx\n", kdf); return CKR_FUNCTION_FAILED; } @@ -469,7 +558,7 @@ static CK_RV policy_update_symmetric(struct policy_private *pp, CK_MECHANISM_INFO_PTR info, - CK_BBOOL isbytes) + CK_BBOOL isbytes, CK_BBOOL isaesxts) { CK_ULONG minsize; @@ -478,6 +567,8 @@ minsize = pp->strengths[pp->minstrengthidx].strength.details.symmetric; if (isbytes == CK_TRUE) minsize /= 8; + if (isaesxts == CK_TRUE) + minsize *= 2; if (minsize > info->ulMaxKeySize) return CKR_MECHANISM_INVALID; if (minsize > info->ulMinKeySize) @@ -587,6 +678,8 @@ case CKM_ECDSA_SHA384: /* Fallthrough */ case CKM_ECDSA_SHA512: + /* Fallthrough */ + case CKM_IBM_ECDSA_OTHER: if (pp->numallowedcurves == 0) { /* No curve allowed */ return CKR_MECHANISM_INVALID; @@ -803,6 +896,55 @@ ((CK_ECDH1_DERIVE_PARAMS *)mech->pParameter)->kdf) != CKR_OK) rv = CKR_FUNCTION_FAILED; break; + case CKM_IBM_ECDSA_OTHER: + switch (((CK_IBM_ECDSA_OTHER_PARAMS *) mech->pParameter)->submechanism) { + case CKM_IBM_ECSDSA_RAND: + case CKM_IBM_ECSDSA_COMPR_MULTI: + /* Uses SHA-256 internally */ + if (hashmap_find(pp->allowedmechs, CKM_SHA256, NULL) == 0) { + TRACE_WARNING("POLICY VIOLATION: ECDSA OTHER SHA-256 algorithm not allowed by policy.\n"); + rv = CKR_FUNCTION_FAILED; + } + break; + default: + rv = CKR_FUNCTION_FAILED; + break; + } + break; + case CKM_IBM_BTC_DERIVE: + if (((CK_IBM_BTC_DERIVE_PARAMS *)mech->pParameter)->version != + CK_IBM_BTC_DERIVE_PARAMS_VERSION_1) + break; + switch (((CK_IBM_BTC_DERIVE_PARAMS *)mech->pParameter)->type) { + case CK_IBM_BTC_BIP0032_PRV2PRV: + case CK_IBM_BTC_BIP0032_PRV2PUB: + case CK_IBM_BTC_BIP0032_PUB2PUB: + case CK_IBM_BTC_BIP0032_MASTERK: + case CK_IBM_BTC_SLIP0010_PRV2PRV: + case CK_IBM_BTC_SLIP0010_PRV2PUB: + case CK_IBM_BTC_SLIP0010_PUB2PUB: + case CK_IBM_BTC_SLIP0010_MASTERK: + /* Uses SHA-512 internally */ + if (hashmap_find(pp->allowedmechs, CKM_SHA512_HMAC, NULL) == 0) { + TRACE_WARNING("POLICY VIOLATION: BTC SHA-512-HMAC algorithm not allowed by policy.\n"); + rv = CKR_FUNCTION_FAILED; + } + break; + default: + rv = CKR_FUNCTION_FAILED; + break; + } + break; + case CKM_IBM_KYBER: + /* Only KEM uses a parameter, KeyGen, Encrypt/Decrypt don't */ + if (mech->ulParameterLen != sizeof(CK_IBM_KYBER_PARAMS)) + break; + if (policy_is_kdf_allowed(pp, + ((CK_IBM_KYBER_PARAMS *)mech->pParameter)->kdf) != CKR_OK) { + rv = CKR_FUNCTION_FAILED; + break; + } + break; default: break; } @@ -820,6 +962,7 @@ /* Silence spurious maybe-uninitialized warning. */ struct objstrength tmp = { 0, 0, CK_TRUE }; const struct mechrow *row; + CK_BBOOL isaesxts = CK_FALSE; if (pp) { if (hashmap_find(pp->allowedmechs, mech, NULL) == 0) @@ -836,7 +979,9 @@ case CKM_AES_CTR: case CKM_AES_ECB: case CKM_AES_GCM: + case CKM_AES_XTS: case CKM_AES_KEY_GEN: + case CKM_AES_XTS_KEY_GEN: case CKM_AES_MAC: case CKM_AES_MAC_GENERAL: case CKM_AES_OFB: @@ -848,7 +993,10 @@ case CKM_SHA512_KEY_DERIVATION: case CKM_SSL3_MASTER_KEY_DERIVE: case CKM_SSL3_PRE_MASTER_KEY_GEN: - if (policy_update_symmetric(pp, info, CK_TRUE) != CKR_OK) { + case CKM_TLS_PRE_MASTER_KEY_GEN: + isaesxts = (mech == CKM_AES_XTS_KEY_GEN || mech == CKM_AES_XTS); + if (policy_update_symmetric(pp, info, CK_TRUE, + isaesxts) != CKR_OK) { row = mechrow_from_numeric(mech); TRACE_DEVEL("Mechanism %s (0x%lx) blocked by policy!\n", row ? row->string : "UNKNOWN", mech); @@ -926,6 +1074,8 @@ case CKM_IBM_EC_C448: case CKM_IBM_ED25519_SHA512: case CKM_IBM_ED448_SHA3: + case CKM_IBM_ECDSA_OTHER: + case CKM_IBM_BTC_DERIVE: if (policy_update_ec(pp, info) != CKR_OK) { TRACE_DEVEL("Mechanism 0x%lx blocked by policy!\n", mech); return CKR_MECHANISM_INVALID; @@ -938,12 +1088,14 @@ case CKM_IBM_SHA3_512_HMAC: case CKM_SSL3_MD5_MAC: case CKM_SSL3_SHA1_MAC: - if (policy_update_symmetric(pp, info, CK_FALSE) != CKR_OK) { + if (policy_update_symmetric(pp, info, CK_FALSE, + CK_FALSE) != CKR_OK) { TRACE_DEVEL("Mechanism 0x%lx blocked by policy!\n", mech); return CKR_MECHANISM_INVALID; } break; case CKM_IBM_DILITHIUM: + case CKM_IBM_KYBER: break; case CKM_IBM_SHA3_224: case CKM_IBM_SHA3_256: @@ -1385,22 +1537,35 @@ i->key, i->line); break; } - if (mgf >= CKG_VENDOR_DEFINED) + if (mgf >= CKG_VENDOR_DEFINED) { + if ((mgf - CKG_VENDOR_DEFINED - 1) > 31) { + TRACE_ERROR("POLICY: MGF invalid: \"%s\" (line %hd)\n", + i->key, i->line); + rc = CKR_FUNCTION_FAILED; + break; + } vmgfs |= (1u << (mgf - CKG_VENDOR_DEFINED - 1)); - else + } else { + if (mgf > 31) { + TRACE_ERROR("POLICY: MGF invalid: \"%s\" (line %hd)\n", + i->key, i->line); + rc = CKR_FUNCTION_FAILED; + break; + } smgfs |= (1u << mgf); + } } } pp->allowedmgfs = smgfs; pp->allowedvendormgfs = vmgfs; - return CKR_OK; + return rc; } static CK_RV policy_parse_kdfs(struct policy_private *pp, struct ConfigBaseNode *list) { struct ConfigBaseNode *i; - CK_ULONG kdfs = 0, kdf; + CK_ULONG kdfs = 0, vkdfs = 0, kdf; CK_RV rc = CKR_OK; int f; @@ -1412,10 +1577,28 @@ i->key, i->line); break; } - kdfs |= (1u << kdf); + + if (kdf >= CKD_VENDOR_DEFINED) { + if ((kdf - CKD_VENDOR_DEFINED - 1) > 31) { + TRACE_ERROR("POLICY: KDF invalid: \"%s\" (line %hd)\n", + i->key, i->line); + rc = CKR_FUNCTION_FAILED; + break; + } + vkdfs |= (1u << (kdf - CKD_VENDOR_DEFINED - 1)); + } else { + if (kdf > 31) { + TRACE_ERROR("POLICY: KDF invalid: \"%s\" (line %hd)\n", + i->key, i->line); + rc = CKR_FUNCTION_FAILED; + break; + } + kdfs |= (1u << kdf); + } } } pp->allowedkdfs = kdfs; + pp->allowedvendorkdfs = vkdfs; return rc; } @@ -1609,6 +1792,7 @@ if (!allowedkdfs) { TRACE_DEVEL("POLICY: No KDF restrictions\n"); pp->allowedkdfs = ~0u; + pp->allowedvendorkdfs = ~0u; } else if (!confignode_hastype(allowedkdfs, CT_BARELIST)) { TRACE_ERROR("POLICY: allowedkdfs has wrong type!\n"); OCK_SYSLOG(LOG_ERR, "POLICY: allowedkdfs has wrong type!\n"); @@ -1703,7 +1887,8 @@ strerror(err)); OCK_SYSLOG(LOG_ERR, "POLICY: Failed to open " OCK_POLICY_CFG ": %s\n", strerror(err)); - return CKR_GENERAL_ERROR; + rc = CKR_GENERAL_ERROR; + goto out; } rc = policy_check_cfg_file(fp, OCK_POLICY_CFG); if (rc != CKR_OK) diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/shrd_mem.c.in opencryptoki-3.20.0+dfsg/usr/lib/api/shrd_mem.c.in --- opencryptoki-3.18.0+dfsg/usr/lib/api/shrd_mem.c.in 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/shrd_mem.c.in 2023-02-13 09:22:42.000000000 +0100 @@ -50,7 +50,7 @@ // by the slot manager daemon. // A NULL pointer will return if the memory region is invalid // for any reason -void *attach_shared_memory() +void *attach_shared_memory(void) { int shmid; char *shmp; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/socket_client.c opencryptoki-3.20.0+dfsg/usr/lib/api/socket_client.c --- opencryptoki-3.18.0+dfsg/usr/lib/api/socket_client.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/socket_client.c 2023-02-13 09:22:42.000000000 +0100 @@ -456,7 +456,7 @@ return NULL; } -int start_event_thread() +int start_event_thread(void) { int rc; @@ -472,7 +472,7 @@ return 0; } -int stop_event_thread() +int stop_event_thread(void) { int rc; void *status; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/statistics.c opencryptoki-3.20.0+dfsg/usr/lib/api/statistics.c --- opencryptoki-3.18.0+dfsg/usr/lib/api/statistics.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/statistics.c 2023-02-13 09:22:42.000000000 +0100 @@ -67,6 +67,9 @@ case CKM_SHA256_RSA_PKCS_PSS: case CKM_SHA384_RSA_PKCS_PSS: case CKM_SHA512_RSA_PKCS_PSS: + if (mech->pParameter == NULL || + mech->ulParameterLen != sizeof(CK_RSA_PKCS_PSS_PARAMS)) + return CKR_MECHANISM_PARAM_INVALID; implicit_mech.mechanism = ((CK_RSA_PKCS_PSS_PARAMS *)mech->pParameter)->hashAlg; rc = statistics_increment(statistics, slot, &implicit_mech, @@ -84,6 +87,9 @@ return rc; break; case CKM_RSA_PKCS_OAEP: + if (mech->pParameter == NULL || + mech->ulParameterLen != sizeof(CK_RSA_PKCS_OAEP_PARAMS)) + return CKR_MECHANISM_PARAM_INVALID; implicit_mech.mechanism = ((CK_RSA_PKCS_OAEP_PARAMS *)mech->pParameter)->hashAlg; rc = statistics_increment(statistics, slot, &implicit_mech, @@ -101,7 +107,11 @@ return rc; break; case CKM_ECDH1_DERIVE: - if (((CK_ECDH1_DERIVE_PARAMS *)mech->pParameter)->kdf == CKD_NULL) + if (mech->pParameter == NULL || + mech->ulParameterLen != sizeof(CK_ECDH1_DERIVE_PARAMS)) + return CKR_MECHANISM_PARAM_INVALID; + if (((CK_ECDH1_DERIVE_PARAMS *)mech->pParameter)->kdf == CKD_NULL || + ((CK_ECDH1_DERIVE_PARAMS *)mech->pParameter)->kdf == CKD_IBM_HYBRID_NULL) break; rc = digest_from_kdf(((CK_ECDH1_DERIVE_PARAMS *)mech->pParameter)->kdf, &implicit_mech.mechanism); @@ -112,6 +122,58 @@ if (rc != CKR_OK) return rc; break; + case CKM_IBM_ECDSA_OTHER: + switch (((CK_IBM_ECDSA_OTHER_PARAMS *)mech->pParameter)->submechanism) { + case CKM_IBM_ECSDSA_RAND: + case CKM_IBM_ECSDSA_COMPR_MULTI: + /* Uses SHA-256 internally */ + implicit_mech.mechanism = CKM_SHA256; + rc = statistics_increment(statistics, slot, &implicit_mech, + POLICY_STRENGTH_IDX_0); + if (rc != CKR_OK) + return rc; + break; + } + break; + case CKM_IBM_BTC_DERIVE: + if (((CK_IBM_BTC_DERIVE_PARAMS *)mech->pParameter)->version != + CK_IBM_BTC_DERIVE_PARAMS_VERSION_1) + break; + switch (((CK_IBM_BTC_DERIVE_PARAMS *)mech->pParameter)->type) { + case CK_IBM_BTC_BIP0032_PRV2PRV: + case CK_IBM_BTC_BIP0032_PRV2PUB: + case CK_IBM_BTC_BIP0032_PUB2PUB: + case CK_IBM_BTC_BIP0032_MASTERK: + case CK_IBM_BTC_SLIP0010_PRV2PRV: + case CK_IBM_BTC_SLIP0010_PRV2PUB: + case CK_IBM_BTC_SLIP0010_PUB2PUB: + case CK_IBM_BTC_SLIP0010_MASTERK: + /* Uses SHA-512 internally */ + implicit_mech.mechanism = CKM_SHA512_HMAC; + rc = statistics_increment(statistics, slot, &implicit_mech, + POLICY_STRENGTH_IDX_0); + if (rc != CKR_OK) + return rc; + break; + } + break; + case CKM_IBM_KYBER: + /* Only KEM uses a parameter, KeyGen, Encrypt/Decrypt don't */ + if (mech->ulParameterLen != sizeof(CK_IBM_KYBER_PARAMS)) + break; + if (((CK_IBM_KYBER_PARAMS *)mech->pParameter)->kdf == CKD_NULL || + ((CK_IBM_KYBER_PARAMS *)mech->pParameter)->kdf == CKD_IBM_HYBRID_NULL) + break; + rc = digest_from_kdf(((CK_IBM_KYBER_PARAMS *)mech->pParameter)->kdf, + &implicit_mech.mechanism); + if (rc != CKR_OK) + return rc; + rc = statistics_increment(statistics, slot, &implicit_mech, + POLICY_STRENGTH_IDX_0); + if (rc != CKR_OK) + return rc; + break; + default: break; } @@ -128,7 +190,7 @@ static CK_RV statistics_open_shm(struct statistics *statistics, int user, CK_BBOOL create) { - int i, err, clear = 0; + int i, err, clear = 0, fd; struct stat stat_buf; snprintf(statistics->shm_name, sizeof(statistics->shm_name) - 1, @@ -145,15 +207,13 @@ TRACE_INFO("Statistics SHM name: '%s'\n", statistics->shm_name); - statistics->shm_handle = shm_open(statistics->shm_name, O_RDWR, - S_IRUSR | S_IWUSR); - if (statistics->shm_handle == -1) { + fd = shm_open(statistics->shm_name, O_RDWR, S_IRUSR | S_IWUSR); + if (fd == -1) { if (create) { /* try to create it */ - statistics->shm_handle = shm_open(statistics->shm_name, - O_CREAT | O_RDWR, - S_IRUSR | S_IWUSR); - if (statistics->shm_handle == -1) { + fd = shm_open(statistics->shm_name, O_CREAT | O_RDWR, + S_IRUSR | S_IWUSR); + if (fd == -1) { err = errno; TRACE_ERROR("Failed to create SHM '%s': %s\n", statistics->shm_name, strerror(err)); @@ -162,13 +222,13 @@ return CKR_FUNCTION_FAILED; } - if (fchmod(statistics->shm_handle, S_IRUSR | S_IWUSR) == -1) { + if (fchmod(fd, S_IRUSR | S_IWUSR) == -1) { err = errno; TRACE_ERROR("Failed to change mode of SHM '%s': %s\n", statistics->shm_name, strerror(err)); OCK_SYSLOG(LOG_ERR, "Failed to change mode of SHM '%s': %s\n", statistics->shm_name, strerror(err)); - close(statistics->shm_handle); + close(fd); shm_unlink(statistics->shm_name); return CKR_FUNCTION_FAILED; } @@ -182,13 +242,13 @@ } } - if (fstat(statistics->shm_handle, &stat_buf)) { + if (fstat(fd, &stat_buf)) { err = errno; TRACE_ERROR("Failed to stat SHM '%s': %s\n", statistics->shm_name, strerror(err)); OCK_SYSLOG(LOG_ERR, "Failed to stat SHM '%s': %s\n", statistics->shm_name, strerror(err)); - close(statistics->shm_handle); + close(fd); return CKR_FUNCTION_FAILED; } @@ -201,19 +261,19 @@ TRACE_ERROR("SHM '%s' has wrong mode/owner\n", statistics->shm_name); OCK_SYSLOG(LOG_ERR, "SHM '%s' has wrong mode/owner\n", statistics->shm_name); - close(statistics->shm_handle); + close(fd); return CKR_FUNCTION_FAILED; } if ((CK_ULONG)stat_buf.st_size != statistics->shm_size) { if (create) { - if (ftruncate(statistics->shm_handle, statistics->shm_size) < 0) { + if (ftruncate(fd, statistics->shm_size) < 0) { err = errno; TRACE_ERROR("Failed to set size of SHM '%s': %s\n", statistics->shm_name, strerror(err)); OCK_SYSLOG(LOG_ERR, "Failed to set size of SHM '%s': %s\n", statistics->shm_name, strerror(err)); - close(statistics->shm_handle); + close(fd); return CKR_FUNCTION_FAILED; } @@ -222,20 +282,21 @@ TRACE_ERROR("SHM '%s' has wrong size\n", statistics->shm_name); OCK_SYSLOG(LOG_ERR, "SHM '%s' has wrong size\n", statistics->shm_name); + close(fd); return CKR_FUNCTION_FAILED; } } statistics->shm_data = (CK_BYTE *)mmap(NULL, statistics->shm_size, PROT_READ | PROT_WRITE, MAP_SHARED, - statistics->shm_handle, 0); + fd, 0); + close(fd); if (statistics->shm_data == MAP_FAILED) { err = errno; TRACE_ERROR("Failed to memory-map SHM '%s': %s\n", statistics->shm_name, strerror(err)); OCK_SYSLOG(LOG_ERR, "Failed to memory-map SHM '%s': %s\n", statistics->shm_name, strerror(err)); - close(statistics->shm_handle); statistics->shm_data = NULL; return CKR_FUNCTION_FAILED; } @@ -251,11 +312,10 @@ { CK_RV rc; - if (statistics->shm_data == NULL || statistics->shm_handle == -1) + if (statistics->shm_data == NULL) return CKR_ARGUMENTS_BAD; munmap(statistics->shm_data, statistics->shm_size); - close(statistics->shm_handle); if (destroy) { rc = shm_unlink(statistics->shm_name); @@ -280,7 +340,6 @@ CK_RV rc; statistics->flags = flags; - statistics->shm_handle = -1; statistics->shm_data = NULL; /* Count number of configured slots and calculate slot offsets. */ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/api/statistics.h opencryptoki-3.20.0+dfsg/usr/lib/api/statistics.h --- opencryptoki-3.18.0+dfsg/usr/lib/api/statistics.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/api/statistics.h 2023-02-13 09:22:42.000000000 +0100 @@ -50,7 +50,6 @@ CK_ULONG slot_shm_offsets[NUMBER_SLOTS_MANAGED]; CK_ULONG shm_size; char shm_name[PATH_MAX]; - int shm_handle; CK_BYTE *shm_data; statistics_increment_f increment_func; /* NULL if statistics disabled */ }; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/cca_func.h opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/cca_func.h --- opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/cca_func.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/cca_func.h 2023-02-13 09:22:42.000000000 +0100 @@ -1302,3 +1302,11 @@ unsigned long *reserved1, long *reserved2_length, unsigned char *reserved2); + +/* Cryptographic Facility Version */ +typedef void (*CSUACFV_t)(long *return_code, + long *reason_code, + long *exit_data_length, + unsigned char *exit_data, + long *version_data_length, + unsigned char *version_data); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/cca_specific.c opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/cca_specific.c --- opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/cca_specific.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/cca_specific.c 2023-02-13 09:22:42.000000000 +0100 @@ -17,6 +17,7 @@ #include #include +#include #include #include #include @@ -27,6 +28,7 @@ #include #include #include +#include #include "cca_stdll.h" #include "pkcs11types.h" #include "p11util.h" @@ -40,6 +42,9 @@ #include "trace.h" #include "ock_syslog.h" #include "cca_func.h" +#include "cfgparser.h" +#include "configuration.h" +#include "events.h" #include /** @@ -71,6 +76,9 @@ #define CCASHAREDLIB "libcsulcca.so" +#define CCA_MIN_VERSION 7 +#define CCA_MIN_RELEASE 1 + static CSNBCKI_t dll_CSNBCKI; static CSNBCKM_t dll_CSNBCKM; static CSNBDKX_t dll_CSNBDKX; @@ -166,6 +174,7 @@ static CSNBHMG_t dll_CSNBHMG; static CSNBHMV_t dll_CSNBHMV; static CSNBCTT2_t dll_CSNBCTT2; +static CSUACFV_t dll_CSUACFV; /* mechanisms provided by this token */ static const MECH_LIST_ELEMENT cca_mech_list[] = { @@ -196,12 +205,10 @@ {24, 24, CKF_HW | CKF_ENCRYPT | CKF_DECRYPT}}, {CKM_DES3_CBC_PAD, {24, 24, CKF_HW | CKF_ENCRYPT | CKF_DECRYPT}}, -#ifndef NOAES {CKM_AES_KEY_GEN, {16, 32, CKF_HW | CKF_GENERATE}}, {CKM_AES_ECB, {16, 32, CKF_HW | CKF_ENCRYPT | CKF_DECRYPT}}, {CKM_AES_CBC, {16, 32, CKF_HW | CKF_ENCRYPT | CKF_DECRYPT}}, {CKM_AES_CBC_PAD, {16, 32, CKF_HW | CKF_ENCRYPT | CKF_DECRYPT}}, -#endif {CKM_SHA512, {0, 0, CKF_HW | CKF_DIGEST}}, {CKM_SHA512_HMAC, {256, 2048, CKF_SIGN | CKF_VERIFY}}, {CKM_SHA512_HMAC_GENERAL, {256, 2048, CKF_SIGN | CKF_VERIFY}}, @@ -250,14 +257,49 @@ sec_ecc_publ_key }; +/* CCA token private data */ +struct cca_private_data { + void *lib_csulcca; + struct { + unsigned int ver; + unsigned int rel; + unsigned int mod; + } version; + unsigned char expected_sym_mkvp[CCA_MKVP_LENGTH]; + unsigned char expected_aes_mkvp[CCA_MKVP_LENGTH]; + unsigned char expected_apka_mkvp[CCA_MKVP_LENGTH]; + CK_BBOOL expected_sym_mkvp_set; + CK_BBOOL expected_aes_mkvp_set; + CK_BBOOL expected_apka_mkvp_set; + CK_BBOOL dev_any; + CK_BBOOL dom_any; + unsigned int num_adapters; + unsigned int num_domains; + unsigned int num_usagedoms; + unsigned short usage_domains[256]; + CK_BBOOL inconsistent; + char serialno[9]; +}; + +#define CCA_CFG_EXPECTED_MKVPS "EXPECTED_MKVPS" +#define CCA_CFG_SYM_MKVP "SYM" +#define CCA_CFG_AES_MKVP "AES" +#define CCA_CFG_APKA_MKVP "APKA" + +#define SYSFS_DEVICES_AP "/sys/devices/ap/" +#define MASK_COPRO 0x10000000 + +const unsigned char cca_zero_mkvp[CCA_MKVP_LENGTH] = { 0 }; + /* * Helper function: Analyse given CCA token. - * returns TRUE and keytype and keybitsize if token is known and seems - * to be valid (only basic checks are done), otherwise FALSE. + * returns TRUE and keytype, keybitsize, and MKVP address if token is known + * and seems to be valid (only basic checks are done), otherwise FALSE. */ static CK_BBOOL analyse_cca_key_token(const CK_BYTE *t, CK_ULONG tlen, enum cca_token_type *keytype, - unsigned int *keybitsize) + unsigned int *keybitsize, + const CK_BYTE **mkvp) { if (t[0] == 0x01 && (t[4] == 0x00 || t[4] == 0x01)) { /* internal secure cca des data key with exact 64 bytes */ @@ -276,6 +318,7 @@ TRACE_DEVEL("CCA DES data key token has invalid/unknown keysize 0x%02x\n", (int)t[59]); return FALSE; } + *mkvp = &t[8]; return TRUE; } @@ -291,6 +334,7 @@ TRACE_DEVEL("CCA AES data key token has invalid/unknown keybitsize %u\n", *keybitsize); return FALSE; } + *mkvp = &t[8]; return TRUE; } @@ -303,6 +347,7 @@ } *keytype = sec_aes_cipher_key; *keybitsize = 0; /* no chance to find out the key bit size */ + *mkvp = &t[10]; return TRUE; } @@ -336,6 +381,7 @@ TRACE_DEVEL("CCA HMAC key token has invalid/unknown payload bit size %u\n", *keybitsize); return FALSE; } + *mkvp = &t[10]; return TRUE; } @@ -356,6 +402,10 @@ n = *((uint16_t *)(t + CCA_RSA_INTTOK_PRIVKEY_OFFSET + privsec_len + 8)); *keytype = sec_rsa_priv_key; *keybitsize = n; + if (t[CCA_RSA_INTTOK_PRIVKEY_OFFSET] == 0x30) + *mkvp = &t[CCA_RSA_INTTOK_PRIVKEY_OFFSET + 104]; + else + *mkvp = &t[CCA_RSA_INTTOK_PRIVKEY_OFFSET + 116]; return TRUE; } @@ -365,6 +415,7 @@ n = *((uint16_t *)(t + CCA_RSA_INTTOK_HDR_LENGTH + 8)); *keytype = sec_rsa_publ_key; *keybitsize = n; + *mkvp = NULL; return TRUE; } @@ -382,6 +433,7 @@ ec_curve_bits = *((uint16_t *)(t + 8 + 12)); *keytype = sec_ecc_priv_key; *keybitsize = ec_curve_bits; + *mkvp = &t[8+16]; return TRUE; } @@ -391,12 +443,64 @@ ec_curve_bits = *((uint16_t *)(t + 8 + 10)); *keytype = sec_ecc_publ_key; *keybitsize = ec_curve_bits; + *mkvp = NULL; return TRUE; } return FALSE; } +static CK_RV check_expected_mkvp(STDLL_TokData_t *tokdata, + enum cca_token_type keytype, + const CK_BYTE *mkvp) +{ + struct cca_private_data *cca_private = tokdata->private_data; + const char *mktype; + const CK_BYTE *expected_mkvp; + + switch (keytype) { + case sec_des_data_key: + expected_mkvp = cca_private->expected_sym_mkvp; + mktype = "SYM"; + break; + + case sec_aes_data_key: + case sec_aes_cipher_key: + case sec_hmac_key: + expected_mkvp = cca_private->expected_aes_mkvp; + mktype = "AES"; + break; + + case sec_rsa_priv_key: + case sec_ecc_priv_key: + expected_mkvp = cca_private->expected_apka_mkvp; + mktype = "APKA"; + break; + + case sec_rsa_publ_key: + case sec_ecc_publ_key: + /* no MKVP checks for public keys */ + return CKR_OK; + + default: + TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); + return CKR_FUNCTION_FAILED; + } + + if (memcmp(mkvp, expected_mkvp, CCA_MKVP_LENGTH) != 0) { + TRACE_ERROR("The key's master key verification pattern does not " + "match the expected CCA %s master key\n", mktype); + TRACE_DEBUG_DUMP("MKVP of key: ", (CK_BYTE *)mkvp, CCA_MKVP_LENGTH); + TRACE_DEBUG_DUMP("Expected MKVP: ", (CK_BYTE *)expected_mkvp, + CCA_MKVP_LENGTH); + OCK_SYSLOG(LOG_ERR, "The key's master key verification pattern does not " + "match the expected CCA %s master key\n", mktype); + return CKR_DEVICE_ERROR; + } + + return CKR_OK; +} + /* Helper function: build attribute and update template */ static CK_RV build_update_attribute(TEMPLATE * tmpl, CK_ATTRIBUTE_TYPE type, @@ -557,6 +661,7 @@ *(void **)(&dll_CSNBHMG) = dlsym(hdl, "CSNBHMG"); *(void **)(&dll_CSNBHMV) = dlsym(hdl, "CSNBHMV"); *(void **)(&dll_CSNBCTT2) = dlsym(hdl, "CSNBCTT2"); + *(void **)(&dll_CSUACFV) = dlsym(hdl, "CSUACFV"); if ((error = dlerror()) != NULL) { OCK_SYSLOG(LOG_ERR, "%s\n", error); @@ -567,89 +672,763 @@ return CKR_OK; } -CK_RV token_specific_init(STDLL_TokData_t * tokdata, CK_SLOT_ID SlotNumber, - char *conf_name) +static CK_RV cca_get_version(STDLL_TokData_t *tokdata) +{ + struct cca_private_data *cca_private = tokdata->private_data; + unsigned char exit_data[4] = { 0, }; + unsigned char version_data[20] = { 0 }; + long return_code, reason_code; + long version_data_length; + long exit_data_len = 0; + char date[20]; + + /* Get CCA host library version */ + version_data_length = sizeof(version_data); + dll_CSUACFV(&return_code, &reason_code, + &exit_data_len, exit_data, + &version_data_length, version_data); + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFV failed. return:%ld, reason:%ld\n", + return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + version_data[sizeof(version_data) - 1] = '\0'; + TRACE_DEVEL("CCA Version string: %s\n", version_data); + + if (sscanf((char *)version_data, "%u.%u.%uz%s", + &cca_private->version.ver, + &cca_private->version.rel, + &cca_private->version.mod, date) != 4) { + TRACE_ERROR("CCA library version is invalid: %s\n", version_data); + return CKR_FUNCTION_FAILED; + } + + if (cca_private->version.ver < CCA_MIN_VERSION || + (cca_private->version.ver == CCA_MIN_VERSION && + cca_private->version.rel < CCA_MIN_RELEASE)) { + TRACE_ERROR("The CCA host library version is too old: %u.%u.%u, " + "required: %u.%u or later\n", + cca_private->version.ver, cca_private->version.rel, + cca_private->version.mod, CCA_MIN_VERSION, CCA_MIN_RELEASE); + OCK_SYSLOG(LOG_ERR,"The CCA host library version is too old: %u.%u.%u, " + "required: %u.%u or later\n", + cca_private->version.ver, cca_private->version.rel, + cca_private->version.mod, CCA_MIN_VERSION, CCA_MIN_RELEASE); + return CKR_DEVICE_ERROR; + } + + return CKR_OK; +} + +static CK_RV cca_cmp_mkvp(unsigned char mkvp[CCA_MKVP_LENGTH], + unsigned char exp_mkvp[CCA_MKVP_LENGTH], + const char *mktype, const char *adapter, + const char *domain, CK_BBOOL expected_mkvps_set) +{ + if (expected_mkvps_set == FALSE && + memcmp(exp_mkvp, cca_zero_mkvp, CCA_MKVP_LENGTH) == 0) { + /* zero expected MKVP, copy current one */ + memcpy(exp_mkvp, mkvp, CCA_MKVP_LENGTH); + } else { + if (memcmp(mkvp, exp_mkvp, CCA_MKVP_LENGTH) != 0) { + TRACE_ERROR("CCA %s master key on adapter %s domain %s does not " + "match the %s master key\n", mktype, adapter, + domain, expected_mkvps_set ? "expected" : "other APQN's"); + OCK_SYSLOG(LOG_ERR, "CCA %s master key on adapter %s domain %s does " + "not match the %s master key\n", mktype, adapter, + domain, expected_mkvps_set ? "expected" : "other APQN's"); + return CKR_DEVICE_ERROR; + } + } + + return CKR_OK; +} + +static CK_RV cca_get_and_check_mkvps(STDLL_TokData_t *tokdata, + const char *adapter, const char *domain) { + struct cca_private_data *cca_private = tokdata->private_data; unsigned char rule_array[256] = { 0, }; + unsigned char verb_data[256] = { 0, }; long return_code, reason_code, rule_array_count, verb_data_length; - void *lib_csulcca; + unsigned short *id; + CK_RV rc; + + /* Get current adapter serial number */ + memcpy(rule_array, "STATCRD2", 8); + rule_array_count = 1; + verb_data_length = 0; + dll_CSUACFQ(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &verb_data_length, NULL); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFQ (STATCRD2) failed for %s/%s. return:%ld, reason:%ld\n", + adapter, domain, return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + TRACE_DEVEL("%s serialno: %.8s\n", adapter, &rule_array[14 * 8]); + + /* Get status of AES master key (DES, 3DES keys) */ + memcpy(rule_array, "STATCCAE", 8); + rule_array_count = 1; + verb_data_length = 0; + dll_CSUACFQ(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &verb_data_length, NULL); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFQ (STATCCAE) failed for %s/%s. return:%ld, reason:%ld\n", + adapter, domain, return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + /* This value should be 2 if the master key is set in the card */ + if (memcmp(&rule_array[CCA_STATCCAE_CMK_OFFSET], "2 ", 8)) { + TRACE_ERROR("CCA SYM master key is not yet loaded on adapter %s domain %s\n", + adapter, domain); + OCK_SYSLOG(LOG_ERR, + "CCA SYM master key is not yet loaded on adapter %s domain %s\n", + adapter, domain); + return CKR_DEVICE_ERROR; + } + + /* Get status of AES master key (AES, HMAC keys) */ + memset(rule_array, 0, sizeof(rule_array)); + memcpy(rule_array, "STATAES ", 8); + rule_array_count = 1; + verb_data_length = 0; + dll_CSUACFQ(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &verb_data_length, NULL); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFQ (STATAES) failed for %s/%s. return:%ld, reason:%ld\n", + adapter, domain, return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + /* This value should be 2 if the master key is set in the card */ + if (memcmp(&rule_array[CCA_STATAES_CMK_OFFSET], "2 ", 8)) { + TRACE_ERROR("CCA AES master key is not yet loaded on adapter %s domain %s\n", + adapter, domain); + OCK_SYSLOG(LOG_ERR, + "CCA AES master key is not yet loaded on adapter %s domain %s\n", + adapter, domain); + return CKR_DEVICE_ERROR; + } + + /* Get status of APKA master key (RSA and ECC keys) */ + memset(rule_array, 0, sizeof(rule_array)); + memcpy(rule_array, "STATAPKA", 8); + rule_array_count = 1; + verb_data_length = 0; + dll_CSUACFQ(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &verb_data_length, NULL); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFQ (STATAPKA) failed for %s/%s. return:%ld, reason:%ld\n", + adapter, domain, return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + if (memcmp(&rule_array[CCA_STATAPKA_CMK_OFFSET], "2 ", 8)) { + TRACE_ERROR("CCA APKA master key is not yet loaded on adapter %s domain %s\n", + adapter, domain); + OCK_SYSLOG(LOG_ERR, + "CCA APKA master key is not yet loaded on adapter %s domain %s\n", + adapter, domain); + return CKR_DEVICE_ERROR; + } + + /* Get master key verification patterns */ + memset(rule_array, 0, sizeof(rule_array)); + memcpy(rule_array, "STATICSB", 8); + rule_array_count = 1; + verb_data_length = sizeof(verb_data); + dll_CSUACFQ(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &verb_data_length, verb_data); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFQ (STATICSB) failed for %s/%s. return:%ld, reason:%ld\n", + adapter, domain, return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + id = (unsigned short *)(verb_data + CCA_STATICSB_SYM_CMK_ID_OFFSET); + if (*id != CCA_STATICSB_SYM_CMK_ID) { + TRACE_ERROR("CSUACFQ (STATICSB) SYM MKVP not available for %s/%s\n", + adapter, domain); + return CKR_FUNCTION_FAILED; + } + + id = (unsigned short *)(verb_data + CCA_STATICSB_AES_CMK_ID_OFFSET); + if (*id != CCA_STATICSB_AES_CMK_ID) { + TRACE_ERROR("CSUACFQ (STATICSB) AES MKVP not available for %s/%s\n", + adapter, domain); + return CKR_FUNCTION_FAILED; + } + + id = (unsigned short *)(verb_data + CCA_STATICSB_APKA_CMK_ID_OFFSET); + if (*id != CCA_STATICSB_APKA_CMK_ID) { + TRACE_ERROR("CSUACFQ (STATICSB) APKA MKVP not available for %s/%s\n", + adapter, domain); + return CKR_FUNCTION_FAILED; + } + + TRACE_DEBUG("Master key verification patterns for %s/%s\n", + adapter, domain); + TRACE_DEBUG_DUMP("SYM MKVP: ", + verb_data + CCA_STATICSB_SYM_CMK_MKVP_OFFSET, + CCA_MKVP_LENGTH); + TRACE_DEBUG_DUMP("AES MKVP: ", + verb_data + CCA_STATICSB_AES_CMK_MKVP_OFFSET, + CCA_MKVP_LENGTH); + TRACE_DEBUG_DUMP("APKA MKVP: ", + verb_data + CCA_STATICSB_APKA_CMK_MKVP_OFFSET, + CCA_MKVP_LENGTH); + + rc = cca_cmp_mkvp(verb_data + CCA_STATICSB_SYM_CMK_MKVP_OFFSET, + cca_private->expected_sym_mkvp, + "SYM", adapter, domain, + cca_private->expected_sym_mkvp_set); + rc |= cca_cmp_mkvp(verb_data + CCA_STATICSB_AES_CMK_MKVP_OFFSET, + cca_private->expected_aes_mkvp, + "AES", adapter, domain, + cca_private->expected_aes_mkvp_set); + rc |= cca_cmp_mkvp(verb_data + CCA_STATICSB_APKA_CMK_MKVP_OFFSET, + cca_private->expected_apka_mkvp, + "APKA", adapter, domain, + cca_private->expected_apka_mkvp_set); + if (rc != CKR_OK) + return CKR_DEVICE_ERROR; + + return CKR_OK; +} + +static CK_RV cca_check_mkvps_domains(STDLL_TokData_t *tokdata, + const char *device) +{ + struct cca_private_data *cca_private = tokdata->private_data; + unsigned char rule_array[256] = { 0, }; + long return_code, reason_code, rule_array_count, device_name_len; + unsigned char *device_name; + char tmp_str[20]; + unsigned int i, num_found = 0; + CK_RV rc2, rc = CKR_OK; + + for (i = 0; i < cca_private->num_usagedoms; i++) { + /* Allocate the adapter based on device or serialno and domain */ + if (cca_private->dev_any) { + memcpy(rule_array, "DEVICE ", 8); + rule_array_count = 1; + device_name_len = strlen(device); + device_name = (unsigned char *)device; + } else { + memcpy(rule_array, "SERIAL ", 8); + rule_array_count = 1; + device_name_len = strlen(cca_private->serialno); + device_name = (unsigned char *)cca_private->serialno; + } + + if (cca_private->dom_any) { + sprintf((char *)(rule_array + 8), "DOMN%04u", + cca_private->usage_domains[i]); + rule_array_count = 2; + + snprintf(tmp_str, sizeof(tmp_str), "%u", + cca_private->usage_domains[i]); + tmp_str[sizeof(tmp_str) - 1] = '\0'; + } else { + strcpy(tmp_str, "DEFAULT"); + } + + dll_CSUACRA(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &device_name_len, device_name); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACRA failed for %s/%s. return:%ld, reason:%ld\n", + device_name, tmp_str, return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + rc2 = cca_get_and_check_mkvps(tokdata, device, tmp_str); + if (rc2 == CKR_OK) + num_found++; + if (rc2 == CKR_FUNCTION_FAILED) /* device not available, ignore */ + rc2 = CKR_OK; + rc |= rc2; + + /* Deallocate the adapter */ + if (cca_private->dom_any) { + memcpy(rule_array + 8, "DOMN-DEF", 8); + rule_array_count = 2; + } + + dll_CSUACRD(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &device_name_len, device_name); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACRA failed for %s/%s. return:%ld, reason:%ld\n", + device_name, tmp_str, return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + if (cca_private->dom_any == FALSE) + break; + } + + if (rc != CKR_OK) + return CKR_DEVICE_ERROR; + if (num_found == 0) /* none available */ + return CKR_FUNCTION_FAILED; + return CKR_OK; +} + +static CK_RV cca_check_mks(STDLL_TokData_t *tokdata) +{ + struct cca_private_data *cca_private = tokdata->private_data; + unsigned char rule_array[256] = { 0, }; + long return_code, reason_code, rule_array_count, verb_data_length; + unsigned int i, adapter, num_found = 0; + char device_name[9]; + const char *val; + CK_RV rc; + + /* Perform basic queries only once */ + if (cca_private->num_adapters != 0) + goto iterate; + + /* Check if adapter and/or domain auto-selection is used */ + val = getenv(CCA_DEFAULT_ADAPTER_ENVAR); + if (val != NULL && strcmp(val, CCA_DEVICE_ANY) == 0) + cca_private->dev_any = TRUE; + TRACE_DEVEL("dev_any: %d\n", cca_private->dev_any); + + val = getenv(CCA_DEFAULT_DOMAIN_ENVAR); + if (val != NULL && strcmp(val, CCA_DOMAIN_ANY) == 0) + cca_private->dom_any = TRUE; + TRACE_DEVEL("dom_any: %d\n", cca_private->dom_any); + + /* Get number of adapters, current adapter serial number */ + memcpy(rule_array, "STATCRD2", 8); + rule_array_count = 1; + verb_data_length = 0; + dll_CSUACFQ(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &verb_data_length, NULL); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFQ (STATCRD2) failed. return:%ld, reason:%ld\n", + return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + rule_array[8] = '\0'; + if (sscanf((char *)rule_array, "%u", &cca_private->num_adapters) != 1) { + TRACE_ERROR("Failed to parse STATCRD2 output: number of adapters: %s\n", + rule_array); + return CKR_FUNCTION_FAILED; + } + TRACE_DEVEL("num_adapters: %u\n", cca_private->num_adapters); + + memcpy(cca_private->serialno, &rule_array[14 * 8], 8); + cca_private->serialno[8] = '\0'; + TRACE_DEVEL("serialno: %s\n", cca_private->serialno); + + /* Get number of domains */ + memcpy(rule_array, "DOM-NUMS", 8); + rule_array_count = 1; + verb_data_length = sizeof(cca_private->num_domains); + dll_CSUACFQ(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &verb_data_length, (unsigned char *)&cca_private->num_domains); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFQ (DOM-NUMS) failed. return:%ld, reason:%ld\n", + return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + TRACE_DEVEL("num_domains: %u\n", cca_private->num_domains); + + /* Get usage domain mask */ + memcpy(rule_array, "DOM-USAG", 8); + rule_array_count = 1; + verb_data_length = sizeof(cca_private->usage_domains); + dll_CSUACFQ(&return_code, &reason_code, + NULL, NULL, + &rule_array_count, rule_array, + &verb_data_length, (unsigned char *)cca_private->usage_domains); + + if (return_code != CCA_SUCCESS) { + TRACE_ERROR("CSUACFQ (DOM-USAG) failed. return:%ld, reason:%ld\n", + return_code, reason_code); + return CKR_FUNCTION_FAILED; + } + + for (i = 0; i < cca_private->num_domains && + (i + 1) * (unsigned int)sizeof(unsigned short) <= + verb_data_length; i++) { + TRACE_DEVEL("usage_domains[%u] = %u\n", i, cca_private->usage_domains[i]); + } + cca_private->num_usagedoms = i; + TRACE_DEVEL("num_usagedoms: %u\n", cca_private->num_usagedoms); + +iterate: + if (cca_private->dev_any == FALSE && cca_private->dom_any == FALSE) { + /* CCA default adapter and domain selection */ + rc = cca_get_and_check_mkvps(tokdata, "DEFAULT", "DEFAULT"); + if (rc != CKR_OK) + return rc; + } else if (cca_private->dev_any == FALSE) { + /* CCA default adapter selection, but domain ANY */ + rc = cca_check_mkvps_domains(tokdata, "DEFAULT"); + if (rc != CKR_OK) + return rc; + } else { + /* Device ANY and domain ANY or default */ + for (adapter = 1, rc = CKR_OK; adapter <= cca_private->num_adapters; + adapter++) { + sprintf(device_name, "CRP%02u", adapter); + + rc |= cca_check_mkvps_domains(tokdata, device_name); + if (rc == CKR_FUNCTION_FAILED) /* adapter not available, ignore */ + rc = CKR_OK; + if (rc == CKR_OK) + num_found++; + } + if (rc != CKR_OK) + return CKR_DEVICE_ERROR; + if (num_found == 0) + return CKR_FUNCTION_FAILED; + } + + TRACE_DEBUG("Expected master key verification patters (queried):\n"); + if (cca_private->expected_sym_mkvp_set == FALSE) { + TRACE_DEBUG_DUMP("SYM MKVP: ", cca_private->expected_sym_mkvp, + CCA_MKVP_LENGTH); + } else { + TRACE_DEBUG("SYM MKVP: specified in config\n"); + } + if (cca_private->expected_aes_mkvp_set == FALSE) { + TRACE_DEBUG_DUMP("AES MKVP: ", cca_private->expected_aes_mkvp, + CCA_MKVP_LENGTH); + } else { + TRACE_DEBUG("AES MKVP: specified in config\n"); + } + if (cca_private->expected_apka_mkvp_set == FALSE) { + TRACE_DEBUG_DUMP("APKA MKVP: ", cca_private->expected_apka_mkvp, + CCA_MKVP_LENGTH); + } else { + TRACE_DEBUG("APKA MKVP: specified in config\n"); + } + + return CKR_OK; +} + +CK_RV cca_parse_hex(const char *str, unsigned char *bin, size_t size) +{ + unsigned int i, val; + + if (strncasecmp(str, "0x", 2) == 0) + str += 2; + if (strlen(str) != size * 2) + return CKR_FUNCTION_FAILED; + + for (i = 0; i < size; i++) { + if (sscanf(str + (i * 2), "%02x", &val) != 1) + return CKR_FUNCTION_FAILED; + bin[i] = val; + } + + return CKR_OK; +} + +CK_RV cca_config_parse_exp_mkvps(STDLL_TokData_t *tokdata, char *fname, + struct ConfigStructNode *exp_mkvp_node) +{ + struct cca_private_data *cca_private = tokdata->private_data; + struct ConfigBaseNode *c; + char *str; + CK_RV rc = CKR_OK; + int i; + + confignode_foreach(c, exp_mkvp_node->value, i) { + TRACE_DEBUG("Config node: '%s' type: %u line: %u\n", + c->key, c->type, c->line); + + if (strcasecmp(c->key, CCA_CFG_SYM_MKVP) == 0 && + (str = confignode_getstr(c)) != NULL) { + + rc = cca_parse_hex(str, cca_private->expected_sym_mkvp, + CCA_MKVP_LENGTH); + if (rc != CKR_OK) { + OCK_SYSLOG(LOG_ERR, "Error parsing config file '%s': invalid " + "hex value '%s' at line %d\n", fname, + confignode_getstr(c), c->line); + TRACE_ERROR("Error parsing config file '%s': invalid hex value " + "'%s' at line %d\n", fname, confignode_getstr(c), + c->line); + break; + } + + cca_private->expected_sym_mkvp_set = TRUE; + continue; + } + + if (strcasecmp(c->key, CCA_CFG_AES_MKVP) == 0 && + (str = confignode_getstr(c)) != NULL) { + + rc = cca_parse_hex(str, cca_private->expected_aes_mkvp, + CCA_MKVP_LENGTH); + if (rc != CKR_OK) { + OCK_SYSLOG(LOG_ERR, "Error parsing config file '%s': invalid " + "hex value '%s' at line %d\n", fname, + confignode_getstr(c), c->line); + TRACE_ERROR("Error parsing config file '%s': invalid hex value " + "'%s' at line %d\n", fname, confignode_getstr(c), + c->line); + break; + } + + cca_private->expected_aes_mkvp_set = TRUE; + continue; + } + + if (strcasecmp(c->key, CCA_CFG_APKA_MKVP) == 0 && + (str = confignode_getstr(c)) != NULL) { + + rc = cca_parse_hex(str, cca_private->expected_apka_mkvp, + CCA_MKVP_LENGTH); + if (rc != CKR_OK) { + OCK_SYSLOG(LOG_ERR, "Error parsing config file '%s': invalid " + "hex value '%s' at line %d\n", fname, + confignode_getstr(c), c->line); + TRACE_ERROR("Error parsing config file '%s': invalid hex value " + "'%s' at line %d\n", fname, confignode_getstr(c), + c->line); + break; + } + + cca_private->expected_apka_mkvp_set = TRUE; + continue; + } + + OCK_SYSLOG(LOG_ERR, "Error parsing config file '%s': unexpected token " + "'%s' at line %d\n", fname, c->key, c->line); + TRACE_ERROR("Error parsing config file '%s': unexpected token '%s' " + "at line %d\n", fname, c->key, c->line); + return CKR_FUNCTION_FAILED; + } + + TRACE_DEBUG("Expected master key verification patterns\n"); + if (cca_private->expected_sym_mkvp_set == TRUE) { + TRACE_DEBUG_DUMP("SYM MKVP: ", cca_private->expected_sym_mkvp, CCA_MKVP_LENGTH); + } else { + TRACE_DEBUG("SYM MKVP: not specified\n"); + } + if (cca_private->expected_aes_mkvp_set == TRUE) { + TRACE_DEBUG_DUMP("AES MKVP: ", cca_private->expected_aes_mkvp, CCA_MKVP_LENGTH); + } else { + TRACE_DEBUG("AES MKVP: not specified\n"); + } + if (cca_private->expected_apka_mkvp_set == TRUE) { + TRACE_DEBUG_DUMP("APKA MKVP: ", cca_private->expected_apka_mkvp, CCA_MKVP_LENGTH); + } else { + TRACE_DEBUG("APKA MKVP: not specified\n"); + } + + return rc; +} + +static void cca_config_parse_error(int line, int col, const char *msg) +{ + OCK_SYSLOG(LOG_ERR, "Error parsing config file: line %d column %d: %s\n", + line, col, msg); + TRACE_ERROR("Error parsing config file: line %d column %d: %s\n", line, col, + msg); +} + +CK_RV cca_load_config_file(STDLL_TokData_t *tokdata, char *conf_name) +{ + char fname[PATH_MAX]; + FILE *file; + struct ConfigBaseNode *c, *config = NULL; + struct ConfigStructNode *struct_node; + CK_RV rc = CKR_OK; + int ret, i; + + if (conf_name == NULL || strlen(conf_name) == 0) + return CKR_OK; + + if (conf_name[0] == '/') { + /* Absolute path name */ + strncpy(fname, conf_name, sizeof(fname) - 1); + fname[sizeof(fname) - 1] = '\0'; + } else { + /* relative path name */ + snprintf(fname, sizeof(fname), "%s/%s", OCK_CONFDIR, conf_name); + fname[sizeof(fname) - 1] = '\0'; + } + + file = fopen(fname, "r"); + if (file == NULL) { + TRACE_ERROR("%s fopen('%s') failed with errno: %s\n", __func__, fname, + strerror(errno)); + return CKR_FUNCTION_FAILED; + } + + ret = parse_configlib_file(file, &config, cca_config_parse_error, 0); + if (ret != 0) { + TRACE_ERROR("Error parsing config file '%s'\n", fname); + rc = CKR_FUNCTION_FAILED; + goto done; + } + + confignode_foreach(c, config, i) { + TRACE_DEBUG("Config node: '%s' type: %u line: %u\n", + c->key, c->type, c->line); + + if (confignode_hastype(c, CT_FILEVERSION)) { + TRACE_DEBUG("Config file version: '%s'\n", + confignode_to_fileversion(c)->base.key); + continue; + } + + if (confignode_hastype(c, CT_STRUCT)) { + struct_node = confignode_to_struct(c); + if (strcasecmp(struct_node->base.key, CCA_CFG_EXPECTED_MKVPS) == 0) { + rc = cca_config_parse_exp_mkvps(tokdata, fname, struct_node); + if (rc != CKR_OK) + break; + continue; + } + + OCK_SYSLOG(LOG_ERR, "Error parsing config file '%s': unexpected " + "token '%s' at line %d\n", fname, c->key, c->line); + TRACE_ERROR("Error parsing config file '%s': unexpected token '%s' " + "at line %d\n", fname, c->key, c->line); + rc = CKR_FUNCTION_FAILED; + break; + } + + OCK_SYSLOG(LOG_ERR, "Error parsing config file '%s': unexpected token " + "'%s' at line %d\n", fname, c->key, c->line); + TRACE_ERROR("Error parsing config file '%s': unexpected token '%s' " + "at line %d\n", fname, c->key, c->line); + rc = CKR_FUNCTION_FAILED; + break; + } + +done: + confignode_deepfree(config); + fclose(file); + + return rc; +} + +CK_RV token_specific_init(STDLL_TokData_t * tokdata, CK_SLOT_ID SlotNumber, + char *conf_name) +{ + struct cca_private_data *cca_private; + CK_RV rc; UNUSED(conf_name); TRACE_INFO("cca %s slot=%lu running\n", __func__, SlotNumber); + cca_private = calloc(1, sizeof(*cca_private)); + if (cca_private == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + + tokdata->private_data = cca_private; + + rc = cca_load_config_file(tokdata, conf_name); + if (rc != CKR_OK) + goto error; + rc = ock_generic_filter_mechanism_list(tokdata, cca_mech_list, cca_mech_list_len, &(tokdata->mech_list), &(tokdata->mech_list_len)); if (rc != CKR_OK) { TRACE_ERROR("Mechanism filtering failed! rc = 0x%lx\n", rc); - return rc; + goto error; } - lib_csulcca = dlopen(CCASHAREDLIB, RTLD_GLOBAL | RTLD_NOW); - if (lib_csulcca == NULL) { + cca_private->lib_csulcca = dlopen(CCASHAREDLIB, RTLD_GLOBAL | RTLD_NOW); + if (cca_private->lib_csulcca == NULL) { OCK_SYSLOG(LOG_ERR, "%s: Error loading library: '%s' [%s]\n", __func__, CCASHAREDLIB, dlerror()); TRACE_ERROR("%s: Error loading shared library '%s' [%s]\n", __func__, CCASHAREDLIB, dlerror()); - return CKR_FUNCTION_FAILED; + rc = CKR_FUNCTION_FAILED; + goto error; } - rc = cca_resolve_lib_sym(lib_csulcca); - if (rc) - return rc; - - tokdata->private_data = lib_csulcca; - - memcpy(rule_array, "STATCCAE", 8); - - rule_array_count = 1; - verb_data_length = 0; - dll_CSUACFQ(&return_code, - &reason_code, - NULL, - NULL, &rule_array_count, rule_array, &verb_data_length, NULL); + rc = cca_resolve_lib_sym(cca_private->lib_csulcca); + if (rc != CKR_OK) + goto error; - if (return_code != CCA_SUCCESS) { - TRACE_ERROR("CSUACFQ failed. return:%ld, reason:%ld\n", - return_code, reason_code); - return CKR_FUNCTION_FAILED; - } + rc = cca_get_version(tokdata); + if (rc != CKR_OK) + goto error; - /* This value should be 2 if the master key is set in the card */ - if (memcmp(&rule_array[CCA_STATCCAE_SYM_CMK_OFFSET], "2 ", 8)) { - OCK_SYSLOG(LOG_WARNING, - "Warning: CCA symmetric master key is not yet loaded"); - } - if (memcmp(&rule_array[CCA_STATCCAE_ASYM_CMK_OFFSET], "2 ", 8)) { - OCK_SYSLOG(LOG_WARNING, - "Warning: CCA asymmetric master key is not yet loaded"); - } + rc = cca_check_mks(tokdata); + if (rc != CKR_OK) + goto error; return CKR_OK; + +error: + token_specific_final(tokdata, FALSE); + return rc; } CK_RV token_specific_final(STDLL_TokData_t *tokdata, CK_BBOOL in_fork_initializer) { - UNUSED(in_fork_initializer); + struct cca_private_data *cca_private = tokdata->private_data; TRACE_INFO("cca %s running\n", __func__); - free(tokdata->mech_list); + if (tokdata->mech_list != NULL) + free(tokdata->mech_list); - if (tokdata->private_data != NULL && !in_fork_initializer) - dlclose(tokdata->private_data); + if (cca_private != NULL) { + if (cca_private->lib_csulcca != NULL && !in_fork_initializer) + dlclose(cca_private->lib_csulcca); + cca_private->lib_csulcca = NULL; + + free(cca_private); + } tokdata->private_data = NULL; return CKR_OK; } -static CK_RV cca_key_gen(enum cca_key_type type, CK_BYTE * key, - unsigned char *key_form, unsigned char *key_type_1, - CK_ULONG key_size) +static CK_RV cca_key_gen(STDLL_TokData_t *tokdata, + enum cca_key_type type, CK_BYTE * key, + unsigned char *key_form, unsigned char *key_type_1, + CK_ULONG key_size) { long return_code, reason_code; @@ -658,6 +1437,9 @@ unsigned char kek_key_identifier_1[CCA_KEY_ID_SIZE] = { 0, }; unsigned char kek_key_identifier_2[CCA_KEY_ID_SIZE] = { 0, }; unsigned char generated_key_identifier_2[CCA_KEY_ID_SIZE] = { 0, }; + enum cca_token_type keytype; + unsigned int keybitsize; + const CK_BYTE *mkvp; if (type == CCA_DES_KEY) { switch (key_size) { @@ -708,6 +1490,18 @@ return CKR_FUNCTION_FAILED; } + if (analyse_cca_key_token(key, CCA_KEY_ID_SIZE, + &keytype, &keybitsize, &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been generated\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, keytype, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + return CKR_OK; } @@ -718,7 +1512,10 @@ unsigned char key_form[CCA_KEYWORD_SIZE]; unsigned char key_type_1[CCA_KEYWORD_SIZE]; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } *des_key = calloc(CCA_KEY_ID_SIZE, 1); if (*des_key == NULL) @@ -729,7 +1526,8 @@ memcpy(key_form, "OP ", (size_t) CCA_KEYWORD_SIZE); memcpy(key_type_1, "DATA ", (size_t) CCA_KEYWORD_SIZE); - return cca_key_gen(CCA_DES_KEY, *des_key, key_form, key_type_1, keysize); + return cca_key_gen(tokdata, CCA_DES_KEY, *des_key, key_form, + key_type_1, keysize); } @@ -769,7 +1567,10 @@ CK_ATTRIBUTE *attr = NULL; CK_RV rc; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } rc = template_attribute_get_non_empty(key->template, CKA_IBM_OPAQUE, &attr); if (rc != CKR_OK) { @@ -1127,8 +1928,14 @@ CK_RV rv; CK_BYTE_PTR ptr; CK_ULONG tmpsize, tmpexp, tmpbits; - - UNUSED(tokdata); + enum cca_token_type keytype; + unsigned int keybitsize; + const CK_BYTE *mkvp; + + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } rv = template_attribute_get_ulong(publ_tmpl, CKA_MODULUS_BITS, &tmpbits); if (rv != CKR_OK) { @@ -1227,6 +2034,18 @@ return CKR_FUNCTION_FAILED; } + if (analyse_cca_key_token(priv_key_token, priv_key_token_length, + &keytype, &keybitsize, &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been generated\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, keytype, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + TRACE_DEVEL("RSA secure key token generated. size: %ld\n", priv_key_token_length); @@ -1296,7 +2115,10 @@ CK_ATTRIBUTE *attr; CK_RV rc; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } /* Find the secure key token */ rc = template_attribute_get_non_empty(key_obj->template, CKA_IBM_OPAQUE, @@ -1354,7 +2176,10 @@ CK_ATTRIBUTE *attr; CK_RV rc; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } /* Find the secure key token */ rc = template_attribute_get_non_empty(key_obj->template, CKA_IBM_OPAQUE, @@ -1418,10 +2243,14 @@ OBJECT *key_obj = NULL; CK_RV rc; - UNUSED(tokdata); UNUSED(hash); UNUSED(hlen); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + rc = object_mgr_find_in_map1(tokdata, ctx->key, &key_obj, READ_LOCK); if (rc != CKR_OK) { TRACE_DEVEL("object_mgr_find_in_map1 failed\n"); @@ -1531,10 +2360,14 @@ OBJECT *key_obj = NULL; CK_RV rc; - UNUSED(tokdata); UNUSED(hash); UNUSED(hlen); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + rc = object_mgr_find_in_map1(tokdata, ctx->key, &key_obj, READ_LOCK); if (rc != CKR_OK) { TRACE_DEVEL("object_mgr_find_in_map1 failed\n"); @@ -1642,9 +2475,13 @@ CK_ATTRIBUTE *attr; CK_RV rc; - UNUSED(tokdata); UNUSED(sess); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Find the secure key token */ rc = template_attribute_get_non_empty(key_obj->template, CKA_IBM_OPAQUE, &attr); @@ -1698,9 +2535,13 @@ CK_ATTRIBUTE *attr; CK_RV rc; - UNUSED(tokdata); UNUSED(sess); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Find the secure key token */ rc = template_attribute_get_non_empty(key_obj->template, CKA_IBM_OPAQUE, &attr); @@ -1770,9 +2611,13 @@ CK_BYTE *message = NULL; CK_RV rc; - UNUSED(tokdata); UNUSED(sess); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + rc = object_mgr_find_in_map1(tokdata, ctx->key, &key_obj, READ_LOCK); if (rc != CKR_OK) { TRACE_DEVEL("object_mgr_find_in_map1 failed\n"); @@ -1904,9 +2749,13 @@ CK_BYTE *message = NULL; CK_RV rc; - UNUSED(tokdata); UNUSED(sess); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + rc = object_mgr_find_in_map1(tokdata, ctx->key, &key_obj, READ_LOCK); if (rc != CKR_OK) { TRACE_DEVEL("object_mgr_find_in_map1 failed\n"); @@ -2037,8 +2886,6 @@ return rc; } - -#ifndef NOAES CK_RV token_specific_aes_key_gen(STDLL_TokData_t *tokdata, CK_BYTE **aes_key, CK_ULONG *len, CK_ULONG key_size, CK_BBOOL *is_opaque) @@ -2054,7 +2901,10 @@ unsigned char point_to_array_of_zeros = 0; unsigned char mkvp[16] = { 0, }; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } *aes_key = calloc(CCA_KEY_ID_SIZE, 1); if (*aes_key == NULL) @@ -2105,7 +2955,8 @@ memcpy(key_type, "AESTOKEN", (size_t) CCA_KEYWORD_SIZE); memcpy(*aes_key, key_token, (size_t) CCA_KEY_ID_SIZE); - return cca_key_gen(CCA_AES_KEY, *aes_key, key_form, key_type, key_size); + return cca_key_gen(tokdata, CCA_AES_KEY, *aes_key, key_form, + key_type, key_size); } CK_RV token_specific_aes_ecb(STDLL_TokData_t * tokdata, @@ -2126,7 +2977,10 @@ long int key_len; CK_RV rc; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } rc = template_attribute_get_non_empty(key->template, CKA_IBM_OPAQUE, &attr); if (rc != CKR_OK) { @@ -2226,7 +3080,10 @@ long int key_len; CK_RV rc; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } // get the key value rc = template_attribute_get_non_empty(key->template, CKA_IBM_OPAQUE, &attr); @@ -2342,7 +3199,6 @@ return CKR_OK; } -#endif /* See the top of this file for the declarations of mech_list and * mech_list_len. @@ -2556,8 +3412,14 @@ unsigned char *param2 = NULL; uint8_t curve_type; uint16_t curve_bitlen; - - UNUSED(tokdata); + enum cca_token_type keytype; + unsigned int keybitsize; + const CK_BYTE *mkvp; + + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } rv = curve_supported(publ_tmpl, &curve_type, &curve_bitlen); if (rv != CKR_OK) { @@ -2637,6 +3499,18 @@ return CKR_FUNCTION_FAILED; } + if (analyse_cca_key_token(priv_key_token, priv_key_token_length, + &keytype, &keybitsize, &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been generated\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, keytype, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + TRACE_DEVEL("ECC secure private key token generated. size: %ld\n", priv_key_token_length); @@ -2687,9 +3561,13 @@ CK_ATTRIBUTE *attr; CK_RV rc; - UNUSED(tokdata); UNUSED(sess); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Find the secure key token */ rc = template_attribute_get_non_empty(key_obj->template, CKA_IBM_OPAQUE, &attr); @@ -2741,9 +3619,13 @@ CK_ATTRIBUTE *attr; CK_RV rc; - UNUSED(tokdata); UNUSED(sess); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Find the secure key token */ rc = template_attribute_get_non_empty(key_obj->template, CKA_IBM_OPAQUE, &attr); @@ -2769,6 +3651,8 @@ if (return_code == 4 && reason_code == 429) { return CKR_SIGNATURE_INVALID; + } else if (return_code == 12 && reason_code == 769) { + return CKR_SIGNATURE_INVALID; } else if (return_code != CCA_SUCCESS) { TRACE_ERROR("CSNDDSV (EC VERIFY) failed. return:%ld," " reason:%ld\n", return_code, reason_code); @@ -2789,7 +3673,10 @@ CK_ULONG hash_size; struct cca_sha_ctx *cca_ctx; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } switch (mech->mechanism) { case CKM_SHA_1: @@ -2834,7 +3721,10 @@ long return_code, reason_code, rule_array_count = 2; unsigned char rule_array[CCA_RULE_ARRAY_SIZE] = { 0, }; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } if (!ctx || !ctx->context) return CKR_OPERATION_NOT_INITIALIZED; @@ -2901,7 +3791,10 @@ unsigned char *buffer = NULL; int blocksz, blocksz_mask, use_buffer = 0; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } if (!in_data) return CKR_ARGUMENTS_BAD; @@ -3049,7 +3942,10 @@ long return_code, reason_code, rule_array_count = 2; unsigned char rule_array[CCA_RULE_ARRAY_SIZE] = { 0, }; - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } if (!ctx || !ctx->context) return CKR_OPERATION_NOT_INITIALIZED; @@ -3193,7 +4089,10 @@ CK_RV token_specific_hmac_sign_init(STDLL_TokData_t * tokdata, SESSION * sess, CK_MECHANISM * mech, CK_OBJECT_HANDLE key) { - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } return ccatok_hmac_init(&sess->sign_ctx, mech, key); } @@ -3201,7 +4100,10 @@ CK_RV token_specific_hmac_verify_init(STDLL_TokData_t * tokdata, SESSION * sess, CK_MECHANISM * mech, CK_OBJECT_HANDLE key) { - UNUSED(tokdata); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } return ccatok_hmac_init(&sess->verify_ctx, mech, key); } @@ -3325,6 +4227,11 @@ CK_BYTE * in_data, CK_ULONG in_data_len, CK_BYTE * signature, CK_ULONG * sig_len) { + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + return ccatok_hmac(tokdata, &sess->sign_ctx, in_data, in_data_len, signature, sig_len, TRUE); } @@ -3333,6 +4240,11 @@ CK_BYTE * in_data, CK_ULONG in_data_len, CK_BYTE * signature, CK_ULONG sig_len) { + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + return ccatok_hmac(tokdata, &sess->verify_ctx, in_data, in_data_len, signature, &sig_len, FALSE); } @@ -3528,6 +4440,11 @@ CK_RV token_specific_hmac_sign_update(STDLL_TokData_t * tokdata, SESSION * sess, CK_BYTE * in_data, CK_ULONG in_data_len) { + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + return ccatok_hmac_update(tokdata, &sess->sign_ctx, in_data, in_data_len, TRUE); } @@ -3536,6 +4453,11 @@ SESSION * sess, CK_BYTE * in_data, CK_ULONG in_data_len) { + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + return ccatok_hmac_update(tokdata, &sess->verify_ctx, in_data, in_data_len, FALSE); } @@ -3661,6 +4583,11 @@ CK_RV token_specific_hmac_sign_final(STDLL_TokData_t * tokdata, SESSION * sess, CK_BYTE * signature, CK_ULONG * sig_len) { + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + return ccatok_hmac_final(tokdata, &sess->sign_ctx, signature, sig_len, TRUE); } @@ -3669,14 +4596,22 @@ SESSION * sess, CK_BYTE * signature, CK_ULONG sig_len) { + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + return ccatok_hmac_final(tokdata, &sess->verify_ctx, signature, &sig_len, FALSE); } -static CK_RV import_rsa_privkey(TEMPLATE * priv_tmpl) +static CK_RV import_rsa_privkey(STDLL_TokData_t *tokdata, TEMPLATE * priv_tmpl) { CK_RV rc; CK_ATTRIBUTE *opaque_attr = NULL; + enum cca_token_type token_type; + unsigned int token_keybitsize; + const CK_BYTE *mkvp; rc = template_attribute_find(priv_tmpl, CKA_IBM_OPAQUE, &opaque_attr); if (rc == TRUE) { @@ -3684,16 +4619,14 @@ * This is an import of an existing secure rsa private key which * is stored in the CKA_IBM_OPAQUE attribute. */ - - enum cca_token_type token_type; - unsigned int token_keybitsize; CK_BYTE *t, n[CCATOK_MAX_N_LEN], e[CCATOK_MAX_E_LEN]; CK_ULONG n_len = CCATOK_MAX_N_LEN, e_len = CCATOK_MAX_E_LEN; uint16_t privkey_len, pubkey_offset; + CK_BBOOL true = TRUE; if (analyse_cca_key_token(opaque_attr->pValue, opaque_attr->ulValueLen, - &token_type, &token_keybitsize) != TRUE) { + &token_type, &token_keybitsize, &mkvp) != TRUE) { TRACE_ERROR("Invalid/unknown cca token in CKA_IBM_OPAQUE attribute\n"); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -3702,6 +4635,11 @@ return CKR_TEMPLATE_INCONSISTENT; } + if (check_expected_mkvp(tokdata, token_type, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + t = opaque_attr->pValue; privkey_len = cca_rsa_inttok_privkey_get_len(&t[CCA_RSA_INTTOK_PRIVKEY_OFFSET]); pubkey_offset = CCA_RSA_INTTOK_HDR_LENGTH + privkey_len; @@ -3940,6 +4878,18 @@ goto err; } + if (analyse_cca_key_token(target_key_token, target_key_token_length, + &token_type, &token_keybitsize, &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been imported\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, token_type, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Add the key object to the template */ if ((rc = build_update_attribute(priv_tmpl, CKA_IBM_OPAQUE, target_key_token, @@ -3988,9 +4938,10 @@ unsigned int token_keybitsize; CK_BYTE *t, n[CCATOK_MAX_N_LEN], e[CCATOK_MAX_E_LEN]; CK_ULONG n_len = CCATOK_MAX_N_LEN, e_len = CCATOK_MAX_E_LEN; + const CK_BYTE *mkvp; if (analyse_cca_key_token(opaque_attr->pValue, opaque_attr->ulValueLen, - &token_type, &token_keybitsize) != TRUE) { + &token_type, &token_keybitsize, &mkvp) != TRUE) { TRACE_ERROR("Invalid/unknown cca token in CKA_IBM_OPAQUE attribute\n"); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -4144,10 +5095,14 @@ return CKR_OK; } -static CK_RV import_symmetric_key(OBJECT * object, CK_ULONG keytype) +static CK_RV import_symmetric_key(STDLL_TokData_t *tokdata, + OBJECT * object, CK_ULONG keytype) { CK_RV rc; CK_ATTRIBUTE *opaque_attr = NULL; + enum cca_token_type token_type; + unsigned int token_keybitsize; + const CK_BYTE *mkvp; rc = template_attribute_find(object->template, CKA_IBM_OPAQUE, &opaque_attr); if (rc == TRUE) { @@ -4158,14 +5113,11 @@ * check if the template attributes match to the cca key in the * CKA_IBM_OPAQUE attribute. */ - - enum cca_token_type token_type; - unsigned int token_keybitsize; CK_BYTE zorro[32] = { 0 }; CK_BBOOL true = TRUE; if (analyse_cca_key_token(opaque_attr->pValue, opaque_attr->ulValueLen, - &token_type, &token_keybitsize) != TRUE) { + &token_type, &token_keybitsize, &mkvp) != TRUE) { TRACE_ERROR("Invalid/unknown cca token in CKA_IBM_OPAQUE attribute\n"); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -4207,6 +5159,11 @@ return CKR_KEY_FUNCTION_NOT_PERMITTED; } + if (check_expected_mkvp(tokdata, token_type, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* create a dummy CKA_VALUE attribute with the key bit size but all zero */ if ((rc = build_update_attribute(object->template, CKA_VALUE, zorro, token_keybitsize / 8))) { @@ -4263,6 +5220,18 @@ return CKR_FUNCTION_FAILED; } + if (analyse_cca_key_token(target_key_id, CCA_KEY_ID_SIZE, + &token_type, &token_keybitsize, &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been imported\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, token_type, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Add the key object to the template */ if ((rc = build_update_attribute(object->template, CKA_IBM_OPAQUE, target_key_id, CCA_KEY_ID_SIZE))) { @@ -4280,12 +5249,16 @@ return CKR_OK; } -static CK_RV import_generic_secret_key(OBJECT * object) +static CK_RV import_generic_secret_key(STDLL_TokData_t *tokdata, + OBJECT * object) { CK_RV rc; CK_ATTRIBUTE *opaque_attr = NULL; CK_ATTRIBUTE *value_attr = NULL; CK_ULONG keylen, keybitlen; + enum cca_token_type token_type; + unsigned int token_payloadbitsize; + const CK_BYTE *mkvp; rc = template_attribute_find(object->template, CKA_VALUE, &value_attr); if (rc == FALSE) { @@ -4310,13 +5283,11 @@ * check if the template attributes match to the cca key in the * CKA_IBM_OPAQUE attribute. */ - - enum cca_token_type token_type; - unsigned int token_payloadbitsize, plbitsize; + unsigned int plbitsize; CK_BBOOL true = TRUE; if (analyse_cca_key_token(opaque_attr->pValue, opaque_attr->ulValueLen, - &token_type, &token_payloadbitsize) != TRUE) { + &token_type, &token_payloadbitsize, &mkvp) != TRUE) { TRACE_ERROR("Invalid/unknown cca token in CKA_IBM_OPAQUE attribute\n"); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -4327,6 +5298,11 @@ return CKR_TEMPLATE_INCONSISTENT; } + if (check_expected_mkvp(tokdata, token_type, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* calculate expected payload size from the given keybitlen */ plbitsize = (((keybitlen + 32) + 63) & (~63)) + 320; /* and check with the payload size within the cca hmac token */ @@ -4397,6 +5373,19 @@ return CKR_FUNCTION_FAILED; } + if (analyse_cca_key_token(key_token, key_token_len, + &token_type, &token_payloadbitsize, + &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been imported\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, token_type, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Add the key object to the template */ if ((rc = build_update_attribute(object->template, CKA_IBM_OPAQUE, key_token, key_token_len))) { @@ -4632,10 +5621,13 @@ return CKR_OK; } -static CK_RV import_ec_privkey(TEMPLATE *priv_templ) +static CK_RV import_ec_privkey(STDLL_TokData_t *tokdata, TEMPLATE *priv_templ) { CK_RV rc; CK_ATTRIBUTE *opaque_attr = NULL; + enum cca_token_type token_type; + unsigned int token_keybitsize; + const CK_BYTE *mkvp; rc = template_attribute_find(priv_templ, CKA_IBM_OPAQUE, &opaque_attr); if (rc == TRUE) { @@ -4643,13 +5635,11 @@ * This is an import of an existing secure ecc private key which * is stored in the CKA_IBM_OPAQUE attribute. */ - enum cca_token_type token_type; - unsigned int token_keybitsize; CK_BBOOL true = TRUE; CK_BYTE *t; if (analyse_cca_key_token(opaque_attr->pValue, opaque_attr->ulValueLen, - &token_type, &token_keybitsize) != TRUE) { + &token_type, &token_keybitsize, &mkvp) != TRUE) { TRACE_ERROR("Invalid/unknown cca token in CKA_IBM_OPAQUE attribute\n"); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -4658,6 +5648,11 @@ return CKR_TEMPLATE_INCONSISTENT; } + if (check_expected_mkvp(tokdata, token_type, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* check curve and add CKA_EC_PARAMS attribute */ t = opaque_attr->pValue; rc = check_cca_ec_type_and_add_params(t[8+9], token_keybitsize, priv_templ); @@ -4693,7 +5688,6 @@ CK_ULONG privlen = 0, publen = 0; uint8_t curve_type; uint16_t curve_bitlen; - CK_ULONG field_len; /* Check if curve supported and determine curve type and bitlen */ rc = curve_supported(priv_templ, &curve_type, &curve_bitlen); @@ -4712,18 +5706,19 @@ privlen = attr->ulValueLen; privkey = attr->pValue; - /* Find public key data as BER encoded OCTET STRING in template */ - rc = template_attribute_get_non_empty(priv_templ, CKA_EC_POINT, &attr); + /* calculate the public key from the private key */ + rc = template_attribute_get_non_empty(priv_templ, CKA_ECDSA_PARAMS, + &attr); if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_EC_POINT for the key.\n"); + TRACE_ERROR("Could not find CKA_ECDSA_PARAMS for the key.\n"); return rc; } - rc = ber_decode_OCTET_STRING(attr->pValue, &pubkey, &publen, - &field_len); - if (rc != CKR_OK || attr->ulValueLen != field_len) { - TRACE_DEVEL("ber decoding of public key failed\n"); - return CKR_ATTRIBUTE_VALUE_INVALID; + rc = ec_point_from_priv_key(attr->pValue, attr->ulValueLen, + privkey, privlen, &pubkey, &publen); + if (rc != CKR_OK) { + TRACE_ERROR("ec_point_from_priv_key failed.\n"); + return rc; } /* Build key_value_structure */ @@ -4733,6 +5728,7 @@ pubkey, publen, curve_type, curve_bitlen, (unsigned char *)&key_value_structure, &key_value_structure_length); + free(pubkey); if (rc != CKR_OK) return rc; @@ -4781,6 +5777,19 @@ return CKR_FUNCTION_FAILED; } + if (analyse_cca_key_token(target_key_token, target_key_token_length, + &token_type, &token_keybitsize, + &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been imported\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, token_type, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Add key token to template as CKA_IBM_OPAQUE */ if ((rc = build_update_attribute(priv_templ, CKA_IBM_OPAQUE, target_key_token, target_key_token_length))) { @@ -4811,13 +5820,14 @@ */ enum cca_token_type token_type; unsigned int token_keybitsize; + const CK_BYTE *mkvp; CK_BYTE *t, *q; uint16_t q_len; CK_BYTE *ecpoint = NULL; CK_ULONG ecpoint_len; if (analyse_cca_key_token(opaque_attr->pValue, opaque_attr->ulValueLen, - &token_type, &token_keybitsize) != TRUE) { + &token_type, &token_keybitsize, &mkvp) != TRUE) { TRACE_ERROR("Invalid/unknown cca token in CKA_IBM_OPAQUE attribute\n"); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -4952,9 +5962,13 @@ CK_KEY_TYPE keytype; CK_OBJECT_CLASS keyclass; - UNUSED(tokdata); UNUSED(sess); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + if (!object) { TRACE_ERROR("Invalid argument\n"); return CKR_FUNCTION_FAILED; @@ -4989,7 +6003,7 @@ break; case CKO_PRIVATE_KEY: // do import keypair and create opaque object - rc = import_rsa_privkey(object->template); + rc = import_rsa_privkey(tokdata, object->template); if (rc != CKR_OK) { TRACE_DEVEL("RSA private key import failed, rc=0x%lx\n", rc); return rc; @@ -5004,7 +6018,7 @@ case CKK_AES: case CKK_DES: case CKK_DES3: - rc = import_symmetric_key(object, keytype); + rc = import_symmetric_key(tokdata, object, keytype); if (rc != CKR_OK) { TRACE_DEVEL("Symmetric key import failed, rc=0x%lx\n", rc); return rc; @@ -5014,7 +6028,7 @@ attr != NULL ? attr->ulValueLen : 0); break; case CKK_GENERIC_SECRET: - rc = import_generic_secret_key(object); + rc = import_generic_secret_key(tokdata, object); if (rc != CKR_OK) { TRACE_DEVEL("Generic Secret (HMAC) key import failed " " with rc=0x%lx\n", rc); @@ -5037,7 +6051,7 @@ break; case CKO_PRIVATE_KEY: // do import keypair and create opaque object - rc = import_ec_privkey(object->template); + rc = import_ec_privkey(tokdata, object->template); if (rc != CKR_OK) { TRACE_DEVEL("EC private key import failed, rc=0x%lx\n", rc); return rc; @@ -5072,8 +6086,14 @@ unsigned char key_token[CCA_KEY_TOKEN_SIZE] = { 0 }; long key_token_length = sizeof(key_token); unsigned char rule_array[CCA_RULE_ARRAY_SIZE] = { 0 }; - - UNUSED(tokdata); + enum cca_token_type keytype; + unsigned int keybitsize; + const CK_BYTE *mkvp; + + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } rc = template_attribute_get_ulong(template, CKA_VALUE_LEN, &keylength); if (rc != CKR_OK) { @@ -5137,6 +6157,18 @@ return CKR_FUNCTION_FAILED; } + if (analyse_cca_key_token(key_token, key_token_length, + &keytype, &keybitsize, &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been generated\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, keytype, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + /* Add the key object to the template */ rc = build_attribute(CKA_IBM_OPAQUE, key_token, key_token_length, &opaque_key); @@ -5317,7 +6349,8 @@ return CKR_OK; } -static CK_RV ccatok_unwrap_key_rsa_pkcs(CK_MECHANISM *mech, +static CK_RV ccatok_unwrap_key_rsa_pkcs(STDLL_TokData_t *tokdata, + CK_MECHANISM *mech, OBJECT *wrapping_key, OBJECT *key, CK_BYTE *wrapped_key, CK_ULONG wrapped_key_len) @@ -5333,6 +6366,9 @@ CK_KEY_TYPE key_type, cca_key_type; CK_ULONG key_size = 0; CK_RSA_PKCS_OAEP_PARAMS *oaep; + enum cca_token_type keytype; + unsigned int keybitsize; + const CK_BYTE *mkvp; uint16_t val; CK_RV rc; @@ -5463,6 +6499,18 @@ return CKR_FUNCTION_FAILED; } + if (analyse_cca_key_token(buffer, buffer_len, + &keytype, &keybitsize, &mkvp) == FALSE || + mkvp == NULL) { + TRACE_ERROR("Invalid/unknown cca token has been unwrapped\n"); + return CKR_FUNCTION_FAILED; + } + + if (check_expected_mkvp(tokdata, keytype, mkvp) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + switch (buffer[4]) { case 0x00: /* DES key token */ case 0x01: /* DES3 key token */ @@ -5568,9 +6616,13 @@ CK_KEY_TYPE wrap_key_type; CK_RV rc; - UNUSED(tokdata); UNUSED(session); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + *not_opaque = FALSE; rc = template_attribute_get_ulong(wrapping_key->template, CKA_CLASS, @@ -5614,9 +6666,13 @@ CK_BBOOL false = FALSE; CK_RV rc; - UNUSED(tokdata); UNUSED(session); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + *not_opaque = FALSE; rc = template_attribute_get_ulong(unwrapping_key->template, CKA_CLASS, @@ -5640,7 +6696,8 @@ if (unwrap_key_class != CKO_PRIVATE_KEY && unwrap_keytype != CKK_RSA) return CKR_WRAPPING_KEY_TYPE_INCONSISTENT; - rc = ccatok_unwrap_key_rsa_pkcs(mech, unwrapping_key, unwrapped_key, + rc = ccatok_unwrap_key_rsa_pkcs(tokdata, + mech, unwrapping_key, unwrapped_key, wrapped_key, wrapped_key_len); if (rc != CKR_OK) goto error; @@ -5752,11 +6809,15 @@ CK_ULONG max_clear_len, req_out_len; CK_RV rc; - UNUSED(tokdata); UNUSED(session); UNUSED(decr_ctx); UNUSED(encr_ctx); + if (((struct cca_private_data *)tokdata->private_data)->inconsistent) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + rc = template_attribute_get_non_empty(decr_key_obj->template, CKA_IBM_OPAQUE, &decr_key_opaque); if (rc != CKR_OK) { @@ -5904,4 +6965,108 @@ } return CKR_OK; +} + +static CK_RV file_fgets(const char *fname, char *buf, size_t buflen) +{ + FILE *fp; + char *end; + CK_RV rc = CKR_OK; + + buf[0] = '\0'; + + fp = fopen(fname, "r"); + if (fp == NULL) { + TRACE_ERROR("Failed to open file '%s'\n", fname); + return CKR_FUNCTION_FAILED; + } + if (fgets(buf, buflen, fp) == NULL) { + TRACE_ERROR("Failed to read from file '%s'\n", fname); + rc = CKR_FUNCTION_FAILED; + goto out_fclose; + } + + end = memchr(buf, '\n', buflen); + if (end) + *end = 0; + else + buf[buflen - 1] = 0; + + if (strlen(buf) == 0) + rc = CKR_FUNCTION_FAILED; + +out_fclose: + fclose(fp); + return rc; +} + +/* + * ATTENTION: This function is called in a separate thread. All actions + * performed by this function must be thread save and use locks to lock + * against concurrent access by other threads. + */ +static CK_RV cca_handle_apqn_event(STDLL_TokData_t *tokdata, + unsigned int event_type, + event_udev_apqn_data_t *apqn_data) +{ + struct cca_private_data *cca_private = tokdata->private_data; + char fname[290]; + char buf[250]; + CK_RV rc; + unsigned long val; + + UNUSED(event_type); + + sprintf(fname, "%scard%02x/ap_functions", SYSFS_DEVICES_AP, apqn_data->card); + rc = file_fgets(fname, buf, sizeof(buf)); + if (rc != CKR_OK) + return CKR_OK; + if (sscanf(buf, "%lx", &val) != 1) + val = 0x00000000; + if ((val & MASK_COPRO) == 0) + return CKR_OK; + + TRACE_DEVEL("%s Cross checking MKVPs due to event for APQN %02x.%04x\n", + __func__, apqn_data->card, apqn_data->domain); + + rc = cca_check_mks(tokdata); + if (rc != CKR_OK) { + __sync_or_and_fetch(&cca_private->inconsistent, TRUE); + TRACE_ERROR("CCA master key setup is inconsistent, all crypto operations will fail from now on\n"); + OCK_SYSLOG(LOG_ERR, "CCA master key setup is inconsistent, all crypto operations will fail from now on\n"); + } else { + __sync_and_and_fetch(&cca_private->inconsistent, FALSE); + } + + return CKR_OK; +} + +/* + * Called by the event thread, on receipt of an event. + * + * ATTENTION: This function is called in a separate thread. All actions + * performed by this function must be thread save and use locks to lock + * against concurrent access by other threads. + */ +CK_RV token_specific_handle_event(STDLL_TokData_t *tokdata, + unsigned int event_type, + unsigned int event_flags, + const char *payload, + unsigned int payload_len) +{ + UNUSED(event_flags); + + switch (event_type) { + case EVENT_TYPE_APQN_ADD: + case EVENT_TYPE_APQN_REMOVE: + if (payload_len != sizeof(event_udev_apqn_data_t)) + return CKR_FUNCTION_FAILED; + return cca_handle_apqn_event(tokdata, event_type, + (event_udev_apqn_data_t *)payload); + + default: + return CKR_FUNCTION_NOT_SUPPORTED; + } + + return CKR_OK; } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/cca_stdll.h opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/cca_stdll.h --- opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/cca_stdll.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/cca_stdll.h 2023-02-13 09:22:42.000000000 +0100 @@ -81,10 +81,24 @@ #define CCA_RSA_INTTOK_PUBKEY_E_OFFSET 12 /* Offset into the rule_array returned by the STATCCAE command for the * Current Symmetric Master Key register status */ -#define CCA_STATCCAE_SYM_CMK_OFFSET 8 -/* Offset into the rule_array returned by the STATCCAE command for the - * Current Asymmetric Master Key register status */ -#define CCA_STATCCAE_ASYM_CMK_OFFSET 56 +#define CCA_STATCCAE_CMK_OFFSET 8 +/* Offset into the rule_array returned by the STATAES command for the + * Current AES Master Key register status */ +#define CCA_STATAES_CMK_OFFSET 8 +/* Offset into the rule_array returned by the STATAPKA command for the + * Current APKA Master Key register status */ +#define CCA_STATAPKA_CMK_OFFSET 8 +/* Offsets into the verb_data returned by the STATICSB command for the + * Master Key register verification pattern */ +#define CCA_STATICSB_SYM_CMK_ID 0x0f07 +#define CCA_STATICSB_SYM_CMK_ID_OFFSET 134 /* ID = 0x0f01 */ +#define CCA_STATICSB_SYM_CMK_MKVP_OFFSET 136 /* 8 bytes MKVP */ +#define CCA_STATICSB_AES_CMK_ID 0x0f0b +#define CCA_STATICSB_AES_CMK_ID_OFFSET 182 /* ID = 0x0f0b */ +#define CCA_STATICSB_AES_CMK_MKVP_OFFSET 184 /* 8 bytes MKVP */ +#define CCA_STATICSB_APKA_CMK_ID 0x0f0e +#define CCA_STATICSB_APKA_CMK_ID_OFFSET 218 /* ID = 0x0f0e */ +#define CCA_STATICSB_APKA_CMK_MKVP_OFFSET 220 /* 8 bytes MKVP */ /* Offset to start of public RSA key section for an external public RSA key token */ #define CCA_RSA_EXTTOK_PUBKEY_OFFSET 8 /* Offset to length of n within an public RSA key section in an ext public RSA key token */ @@ -103,6 +117,13 @@ CCA_DES_KEY }; +#define CCA_DEFAULT_ADAPTER_ENVAR "CSU_DEFAULT_ADAPTER" +#define CCA_DEFAULT_DOMAIN_ENVAR "CSU_DEFAULT_DOMAIN" +#define CCA_DEVICE_ANY "DEV-ANY" +#define CCA_DOMAIN_ANY "DOM-ANY" + +#define CCA_MKVP_LENGTH 8 + /* CCA STDLL debug logging definitions */ #ifdef DEBUG diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/cca_stdll.mk opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/cca_stdll.mk --- opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/cca_stdll.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/cca_stdll.mk 2023-02-13 09:22:42.000000000 +0100 @@ -6,15 +6,16 @@ usr/lib/cca_stdll/tok_struct.h opencryptoki_stdll_libpkcs11_cca_la_CFLAGS = \ - -DLINUX -DNOCDMF -DNODSA -DNODH -DNOECB \ + -DLINUX -DNODSA -DNODH \ -DTOK_NEW_DATA_STORE=0x0003000c \ -I${srcdir}/usr/lib/cca_stdll -I${srcdir}/usr/lib/common \ -I${srcdir}/usr/include -DSTDLL_NAME=\"ccatok\" \ - -I${top_builddir}/usr/lib/api -I${srcdir}/usr/lib/api + -I${top_builddir}/usr/lib/api -I${srcdir}/usr/lib/api \ + -I${top_builddir}/usr/lib/config -I${srcdir}/usr/lib/config opencryptoki_stdll_libpkcs11_cca_la_LDFLAGS = -shared \ -Wl,-z,defs,-Bsymbolic -lcrypto -lpthread -nostartfiles \ - -Wl,-soname,$@ -lrt -ldl \ + -Wl,-soname,$@ -lrt -ldl -llber \ -Wl,--version-script=${srcdir}/opencryptoki_tok.map opencryptoki_stdll_libpkcs11_cca_la_SOURCES = usr/lib/common/asn1.c \ @@ -38,7 +39,9 @@ usr/lib/common/profile_obj.c usr/lib/cca_stdll/cca_specific.c \ usr/lib/common/attributes.c usr/lib/common/dlist.c \ usr/lib/common/utility_common.c usr/lib/common/ec_supported.c \ - usr/lib/api/policyhelper.c + usr/lib/api/policyhelper.c usr/lib/config/configuration.c \ + usr/lib/config/cfgparse.y usr/lib/config/cfglex.l \ + usr/lib/common/mech_openssl.c usr/lib/common/pqc_supported.c if ENABLE_LOCKS opencryptoki_stdll_libpkcs11_cca_la_SOURCES += \ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/ccatok.conf opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/ccatok.conf --- opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/ccatok.conf 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/ccatok.conf 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,21 @@ +version cca-0 + +# Optionally specify the expected master key verification patterns for the +# SYM, AES, and APKA master key. The CCA token does not use the ASYM master key. +# +# You can use the TKE or panel.exe to query the current master key verification +# pattern: +# panel.exe --mk-query --mktype=SYM --mkregister=CURRENT +# panel.exe --mk-query --mktype=AES --mkregister=CURRENT +# panel.exe --mk-query --mktype=APKA --mkregister=CURRENT +# For SYM, use the hex string under [RND], for AES and APKA use the hex string +# under [VER]. +# For AES and APKA you can also find the master key verification patterns +# in sysfs: 'cat /sys/bus/ap/devices/./mkvps' +# +# EXPECTED_MKVPS +# { +# SYM = "" +# AES = "" +# APKA = "" +# } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/tok_struct.h opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/tok_struct.h --- opencryptoki-3.18.0+dfsg/usr/lib/cca_stdll/tok_struct.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/cca_stdll/tok_struct.h 2023-02-13 09:22:42.000000000 +0100 @@ -103,16 +103,12 @@ &token_specific_hmac_verify_update, &token_specific_hmac_verify_final, &token_specific_generic_secret_key_gen, -#ifndef NOAES + // AES &token_specific_aes_key_gen, + NULL, // aes_xts_key_gen &token_specific_aes_ecb, &token_specific_aes_cbc, -#else - NULL, - NULL, - NULL, -#endif NULL, // aes_ctr NULL, // aes_gcm_init, NULL, // aes_gcm @@ -122,6 +118,7 @@ NULL, // aes_cfb NULL, // aes_mac NULL, // aes_cmac + NULL, // aes_xts // DSA NULL, // dsa_generate_keypair NULL, // dsa_sign @@ -134,7 +131,7 @@ &token_specific_reencrypt_single, NULL, // set_attribute_values NULL, // set_attrs_for_new_object - NULL, // handle_event + &token_specific_handle_event, }; #endif diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/asn1.c opencryptoki-3.20.0+dfsg/usr/lib/common/asn1.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/asn1.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/asn1.c 2023-02-13 09:22:42.000000000 +0100 @@ -24,6 +24,7 @@ #include "host_defs.h" #include "h_extern.h" #include "trace.h" +#include "pqc_defs.h" // @@ -1648,7 +1649,7 @@ CK_ULONG *data_len, CK_ATTRIBUTE *modulus, CK_ATTRIBUTE *publ_exp) { - CK_ULONG len, offset, total, total_len; + CK_ULONG len = 0, offset, total, total_len; CK_RV rc; CK_BYTE *buf = NULL; CK_BYTE *buf2 = NULL; @@ -2205,7 +2206,7 @@ CK_ATTRIBUTE *subprime, CK_ATTRIBUTE *base, CK_ATTRIBUTE *value) { - CK_ULONG len, parm_len, id_len, pub_len, offset, total; + CK_ULONG len = 0, parm_len, id_len, pub_len, offset, total; CK_RV rc = 0; CK_BYTE *buf = NULL; CK_BYTE *buf2 = NULL; @@ -2564,8 +2565,15 @@ return CKR_FUNCTION_FAILED; } - ber_encode_CHOICE(TRUE, 1, &buf2, &len, (CK_BYTE *)val->bv_val, - val->bv_len); + rc = ber_encode_CHOICE(TRUE, 1, &buf2, &len, (CK_BYTE *)val->bv_val, + val->bv_len); + if (rc != 0) { + TRACE_DEVEL("ber_encode_CHOICE failed\n"); + ber_free(ber, 1); + ber_bvfree(val); + return CKR_FUNCTION_FAILED; + } + offset += len; ber_free(ber, 1); ber_bvfree(val); @@ -2642,8 +2650,15 @@ goto error; } - ber_encode_CHOICE(FALSE, 1, &buf2, &len, (CK_BYTE *)val->bv_val, - val->bv_len); + rc = ber_encode_CHOICE(FALSE, 1, &buf2, &len, (CK_BYTE *)val->bv_val, + val->bv_len); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_encode_CHOICE failed\n"); + ber_free(ber, 1); + ber_bvfree(val); + goto error; + } + memcpy(buf + offset, buf2, len); offset += len; free(buf2); @@ -3352,7 +3367,7 @@ CK_ULONG *data_len, CK_ATTRIBUTE *prime, CK_ATTRIBUTE *base, CK_ATTRIBUTE *value) { - CK_ULONG len, parm_len, id_len, pub_len, offset, total; + CK_ULONG len = 0, parm_len, id_len, pub_len, offset, total; CK_RV rc = 0; CK_BYTE *buf = NULL; CK_BYTE *buf2 = NULL; @@ -3485,7 +3500,6 @@ TRACE_DEVEL("%s ber_put_bitstring/ber_flatten failed\n", __func__); ber_free(ber, 1); ber_bvfree(val); - free(buf); free(buf2); return CKR_FUNCTION_FAILED; } @@ -3617,7 +3631,7 @@ * * SEQUENCE (2 elem) * SEQUENCE (2 elem) - * OBJECT IDENTIFIER 1.3.6.1.4.1.2.267.1.6.5 + * OBJECT IDENTIFIER 1.3.6.1.4.1.2.267.xxx * NULL * BIT STRING (1 elem) * SEQUENCE (2 elem) @@ -3625,20 +3639,26 @@ * BIT STRING (13824 bit) = 1728 bytes */ CK_RV ber_encode_IBM_DilithiumPublicKey(CK_BBOOL length_only, - CK_BYTE **data, CK_ULONG *data_len, - CK_ATTRIBUTE *rho, CK_ATTRIBUTE *t1) + CK_BYTE **data, CK_ULONG *data_len, + const CK_BYTE *oid, CK_ULONG oid_len, + CK_ATTRIBUTE *rho, CK_ATTRIBUTE *t1) { CK_BYTE *buf = NULL, *buf2 = NULL, *buf3 = NULL, *buf4 = NULL; - CK_ULONG len, len4, offset, total, total_len; + CK_BYTE *buf5 = NULL, *algid = NULL; + CK_ULONG len = 0, len4, offset, total, total_len, algid_len; CK_RV rc; UNUSED(length_only); offset = 0; rc = 0; - total_len = ber_AlgIdDilithiumLen; + total_len = 0; total = 0; + /* Calculate storage for AlgID sequence */ + rc |= ber_encode_SEQUENCE(TRUE, NULL, &total_len, NULL, + oid_len + ber_NULLLen); + /* Calculate storage for inner sequence */ rc |= ber_encode_INTEGER(TRUE, NULL, &len, NULL, rho->ulValueLen); offset += len; @@ -3672,6 +3692,7 @@ memcpy(buf + offset, buf2, len); offset += len; free(buf2); + buf2 = NULL; rc = ber_encode_BIT_STRING(FALSE, &buf2, &len, t1->pValue, t1->ulValueLen, 0); @@ -3682,6 +3703,7 @@ memcpy(buf + offset, buf2, len); offset += len; free(buf2); + buf2 = NULL; rc = ber_encode_SEQUENCE(FALSE, &buf2, &len, buf, offset); if (rc != CKR_OK) { @@ -3710,12 +3732,30 @@ /* * SEQUENCE (2 elem) - * OBJECT IDENTIFIER 1.3.6.1.4.1.2.267.1.6.5 + * OBJECT IDENTIFIER 1.3.6.1.4.1.2.267.xxx * NULL <- no parms for this oid */ - total_len = 0; - memcpy(buf3 + total_len, ber_AlgIdDilithium, ber_AlgIdDilithiumLen); - total_len += ber_AlgIdDilithiumLen; + buf5 = (CK_BYTE *) malloc(oid_len + ber_NULLLen); + if (!buf5) { + TRACE_ERROR("%s Memory allocation failed\n", __func__); + rc = CKR_HOST_MEMORY; + goto error; + } + memcpy(buf5, oid, oid_len); + memcpy(buf5 + oid_len, ber_NULL, ber_NULLLen); + + rc = ber_encode_SEQUENCE(FALSE, &algid, &algid_len, buf5, + oid_len + ber_NULLLen); + free(buf5); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_SEQUENCE failed with rc=0x%lx\n", __func__, rc); + goto error; + } + + total_len = algid_len; + memcpy(buf3, algid, algid_len); + free(algid); + algid = NULL; /* * BIT STRING (1 elem) @@ -3761,16 +3801,18 @@ CK_RV ber_decode_IBM_DilithiumPublicKey(CK_BYTE *data, - CK_ULONG data_len, - CK_ATTRIBUTE **rho_attr, - CK_ATTRIBUTE **t1_attr) + CK_ULONG data_len, + CK_ATTRIBUTE **rho_attr, + CK_ATTRIBUTE **t1_attr, + CK_ATTRIBUTE **value_attr, + const struct pqc_oid **oid) { CK_ATTRIBUTE *rho_attr_temp = NULL; CK_ATTRIBUTE *t1_attr_temp = NULL; + CK_ATTRIBUTE *value_attr_temp = NULL; - CK_BYTE *algid_DilithiumBase = NULL; - CK_BYTE *algid = NULL; - CK_ULONG algid_len; + CK_BYTE *algoid = NULL; + CK_ULONG algoid_len; CK_BYTE *param = NULL; CK_ULONG param_len; CK_BYTE *val = NULL; @@ -3781,26 +3823,20 @@ CK_ULONG rho_len; CK_BYTE *t1; CK_ULONG t1_len; - CK_ULONG field_len, offset, len; + CK_ULONG field_len, offset, raw_spki_len; CK_RV rc; UNUSED(data_len); // XXX can this parameter be removed ? - rc = ber_decode_SPKI(data, &algid, &algid_len, ¶m, ¶m_len, + rc = ber_decode_SPKI(data, &algoid, &algoid_len, ¶m, ¶m_len, &val, &val_len); if (rc != CKR_OK) { TRACE_DEVEL("ber_decode_SPKI failed\n"); return rc; } - /* Make sure we're dealing with a Dilithium key */ - rc = ber_decode_SEQUENCE((CK_BYTE *)ber_AlgIdDilithium, &algid_DilithiumBase, &len, - &field_len); - if (rc != CKR_OK) { - TRACE_DEVEL("ber_decode_SEQUENCE failed\n"); - return rc; - } - if (memcmp(algid, algid_DilithiumBase, len) != 0) { + *oid = find_pqc_by_oid(dilithium_oids, algoid, algoid_len); + if (*oid == NULL) { TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); return CKR_FUNCTION_FAILED; } @@ -3849,8 +3885,21 @@ goto cleanup; } + /* Add raw SPKI as CKA_VALUE to public key (z/OS ICSF compatibility) */ + rc = ber_decode_SEQUENCE(data, &val, &val_len, &raw_spki_len); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_decode_SEQUENCE failed with rc=0x%lx\n", __func__, rc); + goto cleanup; + } + rc = build_attribute(CKA_VALUE, data, raw_spki_len, &value_attr_temp); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute failed\n"); + goto cleanup; + } + *rho_attr = rho_attr_temp; *t1_attr = t1_attr_temp; + *value_attr = value_attr_temp; return CKR_OK; @@ -3859,6 +3908,8 @@ free(rho_attr_temp); if (t1_attr_temp) free(t1_attr_temp); + if (value_attr_temp) + free(value_attr_temp); return rc; } @@ -3880,18 +3931,20 @@ * } */ CK_RV ber_encode_IBM_DilithiumPrivateKey(CK_BBOOL length_only, - CK_BYTE **data, - CK_ULONG *data_len, - CK_ATTRIBUTE *rho, - CK_ATTRIBUTE *seed, - CK_ATTRIBUTE *tr, - CK_ATTRIBUTE *s1, - CK_ATTRIBUTE *s2, - CK_ATTRIBUTE *t0, - CK_ATTRIBUTE *t1) + CK_BYTE **data, + CK_ULONG *data_len, + const CK_BYTE *oid, CK_ULONG oid_len, + CK_ATTRIBUTE *rho, + CK_ATTRIBUTE *seed, + CK_ATTRIBUTE *tr, + CK_ATTRIBUTE *s1, + CK_ATTRIBUTE *s2, + CK_ATTRIBUTE *t0, + CK_ATTRIBUTE *t1) { CK_BYTE *buf = NULL, *buf2 = NULL, *buf3 = NULL; - CK_ULONG len, len2 = 0, offset; + CK_BYTE *algid = NULL, *algid_buf = NULL; + CK_ULONG len, len2 = 0, offset, algid_len = 0; CK_BYTE version[] = { 0 }; CK_RV rc; @@ -3899,6 +3952,9 @@ offset = 0; rc = 0; + rc |= ber_encode_SEQUENCE(TRUE, NULL, &algid_len, NULL, + oid_len + ber_NULLLen); + rc |= ber_encode_INTEGER(TRUE, NULL, &len, NULL, sizeof(version)); offset += len; rc |= ber_encode_BIT_STRING(TRUE, NULL, &len, NULL, rho->ulValueLen, 0); @@ -3932,7 +3988,7 @@ } rc = ber_encode_PrivateKeyInfo(TRUE, NULL, data_len, - NULL, ber_AlgIdDilithiumLen, + NULL, algid_len, NULL, len); if (rc != CKR_OK) { TRACE_DEVEL("ber_encode_PrivateKeyInfo failed\n"); @@ -4052,10 +4108,28 @@ TRACE_ERROR("ber_encode_SEQUENCE failed\n"); goto error; } + + algid_buf = (CK_BYTE *) malloc(oid_len + ber_NULLLen); + if (!algid_buf) { + TRACE_ERROR("%s Memory allocation failed\n", __func__); + rc = CKR_HOST_MEMORY; + goto error; + } + memcpy(algid_buf, oid, oid_len); + memcpy(algid_buf + oid_len, ber_NULL, ber_NULLLen); + + rc = ber_encode_SEQUENCE(FALSE, &algid, &algid_len, algid_buf, + oid_len + ber_NULLLen); + free(algid_buf); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_SEQUENCE failed with rc=0x%lx\n", __func__, rc); + goto error; + } + rc = ber_encode_PrivateKeyInfo(FALSE, data, data_len, - ber_AlgIdDilithium, - ber_AlgIdDilithiumLen, buf2, len); + algid, algid_len, + buf2, len); if (rc != CKR_OK) { TRACE_ERROR("ber_encode_PrivateKeyInfo failed\n"); } @@ -4067,6 +4141,8 @@ free(buf2); if (buf) free(buf); + if (algid) + free(algid); return rc; } @@ -4088,19 +4164,21 @@ * } */ CK_RV ber_decode_IBM_DilithiumPrivateKey(CK_BYTE *data, - CK_ULONG data_len, - CK_ATTRIBUTE **rho, - CK_ATTRIBUTE **seed, - CK_ATTRIBUTE **tr, - CK_ATTRIBUTE **s1, - CK_ATTRIBUTE **s2, - CK_ATTRIBUTE **t0, - CK_ATTRIBUTE **t1) + CK_ULONG data_len, + CK_ATTRIBUTE **rho, + CK_ATTRIBUTE **seed, + CK_ATTRIBUTE **tr, + CK_ATTRIBUTE **s1, + CK_ATTRIBUTE **s2, + CK_ATTRIBUTE **t0, + CK_ATTRIBUTE **t1, + CK_ATTRIBUTE **value, + const struct pqc_oid **oid) { CK_ATTRIBUTE *rho_attr = NULL, *seed_attr = NULL; CK_ATTRIBUTE *tr_attr = NULL, *s1_attr = NULL, *s2_attr = NULL; - CK_ATTRIBUTE *t0_attr = NULL, *t1_attr = NULL; - CK_BYTE *alg = NULL; + CK_ATTRIBUTE *t0_attr = NULL, *t1_attr = NULL, *value_attr = NULL; + CK_BYTE *algoid = NULL; CK_BYTE *dilithium_priv_key = NULL; CK_BYTE *buf = NULL; CK_BYTE *tmp = NULL; @@ -4108,15 +4186,21 @@ CK_RV rc; /* Check if this is a Dilithium private key */ - rc = ber_decode_PrivateKeyInfo(data, data_len, &alg, &len, + rc = ber_decode_PrivateKeyInfo(data, data_len, &algoid, &len, &dilithium_priv_key); if (rc != CKR_OK) { TRACE_DEVEL("ber_decode_PrivateKeyInfo failed\n"); return rc; } - if (memcmp(alg, ber_AlgIdDilithium, ber_AlgIdDilithiumLen) != 0) { - // probably ought to use a different error + if (len <= ber_NULLLen || + memcmp(algoid + len - ber_NULLLen, ber_NULL, ber_NULLLen) != 0) { + TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); + return CKR_FUNCTION_FAILED; + } + len -= ber_NULLLen; + *oid = find_pqc_by_oid(dilithium_oids, algoid, len); + if (*oid == NULL) { TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); return CKR_FUNCTION_FAILED; } @@ -4272,6 +4356,18 @@ goto cleanup; } + /* Add private key as CKA_VALUE to public key (z/OS ICSF compatibility) */ + rc = ber_decode_SEQUENCE(data, &tmp, &len, &field_len); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_decode_SEQUENCE failed with rc=0x%lx\n", __func__, rc); + goto cleanup; + } + rc = build_attribute(CKA_VALUE, data, field_len, &value_attr); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute for (t1) failed\n"); + goto cleanup; + } + *rho = rho_attr; *seed = seed_attr; *tr = tr_attr; @@ -4279,6 +4375,7 @@ *s2 = s2_attr; *t0 = t0_attr; *t1 = t1_attr; + *value = value_attr; return CKR_OK; @@ -4298,6 +4395,572 @@ free(s2_attr); if (t0_attr) free(t0_attr); + if (value_attr) + free(value_attr); + + return rc; +} + +/** + * An IBM Kyber public key is given by: + * + * SEQUENCE (2 elem) + * SEQUENCE (2 elem) + * OBJECT IDENTIFIER 1.3.6.1.4.1.2.267.5.xxx + * NULL + * BIT STRING (1 elem) + * SEQUENCE (1 elem) + * pk BIT STRING -- public key + */ +CK_RV ber_encode_IBM_KyberPublicKey(CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len, + const CK_BYTE *oid, CK_ULONG oid_len, + CK_ATTRIBUTE *pk) +{ + CK_BYTE *buf = NULL, *buf2 = NULL, *buf3 = NULL, *buf4 = NULL; + CK_BYTE *buf5 = NULL, *algid = NULL; + CK_ULONG len, len4, offset, total, total_len, algid_len; + CK_RV rc; + + UNUSED(length_only); + + offset = 0; + rc = 0; + total_len = 0; + total = 0; + + /* Calculate storage for AlgID sequence */ + rc |= ber_encode_SEQUENCE(TRUE, NULL, &total_len, NULL, + oid_len + ber_NULLLen); + + /* Calculate storage for inner sequence */ + rc |= ber_encode_INTEGER(TRUE, NULL, &len, NULL, pk->ulValueLen); + offset += len; + + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_Int failed with rc=0x%lx\n", __func__, rc); + return rc; + } + + /* Allocate storage for inner sequence */ + buf = (CK_BYTE *) malloc(offset); + if (!buf) { + TRACE_ERROR("%s Memory allocation failed\n", __func__); + return CKR_HOST_MEMORY; + } + + /** + * SEQUENCE (1 elem) + * BIT STRING -> pk + */ + offset = 0; + rc = ber_encode_BIT_STRING(FALSE, &buf2, &len, + pk->pValue, pk->ulValueLen, 0); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_Int failed with rc=0x%lx\n", __func__, rc); + goto error; + } + memcpy(buf + offset, buf2, len); + offset += len; + free(buf2); + buf2 = NULL; + + rc = ber_encode_SEQUENCE(FALSE, &buf2, &len, buf, offset); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_Seq failed with rc=0x%lx\n", __func__, rc); + goto error; + } + free(buf); + buf = NULL; + + /* Calculate length of outer sequence */ + rc = ber_encode_BIT_STRING(TRUE, NULL, &total, buf2, len, 0); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_Oct_Str failed with rc=0x%lx\n", __func__, rc); + goto error; + } else { + total_len += total; + } + + /* Allocate storage for outer sequence and bit string */ + buf3 = (CK_BYTE *) malloc(total_len); + if (!buf3) { + TRACE_ERROR("%s Memory allocation failed\n", __func__); + rc = CKR_HOST_MEMORY; + goto error; + } + + /* + * SEQUENCE (2 elem) + * OBJECT IDENTIFIER 1.3.6.1.4.1.2.267.5.xxx + * NULL <- no parms for this oid + */ + buf5 = (CK_BYTE *) malloc(oid_len + ber_NULLLen); + if (!buf5) { + TRACE_ERROR("%s Memory allocation failed\n", __func__); + rc = CKR_HOST_MEMORY; + goto error; + } + memcpy(buf5, oid, oid_len); + memcpy(buf5 + oid_len, ber_NULL, ber_NULLLen); + + rc = ber_encode_SEQUENCE(FALSE, &algid, &algid_len, buf5, + oid_len + ber_NULLLen); + free(buf5); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_SEQUENCE failed with rc=0x%lx\n", __func__, rc); + goto error; + } + + total_len = algid_len; + memcpy(buf3, algid, algid_len); + free(algid); + algid = NULL; + + /* + * BIT STRING (1 elem) + * SEQUENCE (1 elem) + * BIT STRING -> pk + */ + rc = ber_encode_BIT_STRING(FALSE, &buf4, &len4, buf2, len, 0); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_BIT_STRING failed with rc=0x%lx\n", __func__, rc); + goto error; + } + memcpy(buf3 + total_len, buf4, len4); + total_len += len4; + free(buf4); + buf4 = NULL; + + /** + * SEQUENCE (2 elem) + * SEQUENCE (2 elem) + * OBJECT IDENTIFIER 1.3.6.1.4.1.2.267.5.xxx + * NULL -> no parms for this oid + * BIT STRING (1 elem) + * SEQUENCE (2 elem) + * BIT STRING -> pk + */ + rc = ber_encode_SEQUENCE(FALSE, data, data_len, buf3, total_len); + if (rc != CKR_OK) + TRACE_ERROR("%s ber_encode_Seq failed with rc=0x%lx\n", __func__, rc); + +error: + + if (buf) + free(buf); + if (buf2) + free(buf2); + if (buf3) + free(buf3); + + return rc; +} + +CK_RV ber_decode_IBM_KyberPublicKey(CK_BYTE *data, + CK_ULONG data_len, + CK_ATTRIBUTE **pk_attr, + CK_ATTRIBUTE **value_attr, + const struct pqc_oid **oid) +{ + CK_ATTRIBUTE *pk_attr_temp = NULL; + CK_ATTRIBUTE *value_attr_temp = NULL; + + CK_BYTE *algoid = NULL; + CK_ULONG algoid_len; + CK_BYTE *param = NULL; + CK_ULONG param_len; + CK_BYTE *val = NULL; + CK_ULONG val_len; + CK_BYTE *seq; + CK_ULONG seq_len; + CK_BYTE *pk; + CK_ULONG pk_len; + CK_ULONG field_len, raw_spki_len; + CK_RV rc; + + UNUSED(data_len); // XXX can this parameter be removed ? + + rc = ber_decode_SPKI(data, &algoid, &algoid_len, ¶m, ¶m_len, + &val, &val_len); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_decode_SPKI failed\n"); + return rc; + } + + *oid = find_pqc_by_oid(kyber_oids, algoid, algoid_len); + if (*oid == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); + return CKR_FUNCTION_FAILED; + } + + /* Decode sequence: + * SEQUENCE (1 elem) + * BIT STRING = pk + */ + rc = ber_decode_SEQUENCE(val, &seq, &seq_len, &field_len); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_decode_SEQUENCE failed\n"); + return rc; + } + + /* Decode pk */ + rc = ber_decode_BIT_STRING(seq, &pk, &pk_len, &field_len); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_decode_INTEGER failed\n"); + return rc; + } + pk++; /* Remove unused-bits byte */ + pk_len--; + + /* Build pk attribute */ + rc = build_attribute(CKA_IBM_KYBER_PK, pk, pk_len, &pk_attr_temp); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute failed\n"); + goto cleanup; + } + + /* Add raw SPKI as CKA_VALUE to public key (z/OS ICSF compatibility) */ + rc = ber_decode_SEQUENCE(data, &val, &val_len, &raw_spki_len); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_decode_SEQUENCE failed with rc=0x%lx\n", __func__, rc); + goto cleanup; + } + rc = build_attribute(CKA_VALUE, data, raw_spki_len, &value_attr_temp); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute failed\n"); + goto cleanup; + } + + *pk_attr = pk_attr_temp; + *value_attr = value_attr_temp; + + return CKR_OK; + +cleanup: + if (pk_attr_temp) + free(pk_attr_temp); + if (value_attr_temp) + free(value_attr_temp); return rc; } + +/** + * An IBM Kyber private key is given by: + * + * KyberPrivateKey ::= SEQUENCE { + * version INTEGER, -- v0, reserved 0 + * sk BIT STRING, -- private key + * pk [0] IMPLICIT OPTIONAL { + * pk||rs BIT STRING -- public key (pk) concatenated with 2x32 bytes rs + * } + * } + */ +CK_RV ber_encode_IBM_KyberPrivateKey(CK_BBOOL length_only, + CK_BYTE **data, + CK_ULONG *data_len, + const CK_BYTE *oid, CK_ULONG oid_len, + CK_ATTRIBUTE *sk, + CK_ATTRIBUTE *pk) +{ + CK_BYTE *buf = NULL, *buf2 = NULL, *buf3 = NULL; + CK_BYTE *algid = NULL, *algid_buf = NULL, *pk_rs = NULL; + CK_ULONG len, len2 = 0, offset, algid_len = 0; + CK_BYTE version[] = { 0 }; + CK_RV rc; + + /* Calculate storage for sequence */ + offset = 0; + rc = 0; + + rc |= ber_encode_SEQUENCE(TRUE, NULL, &algid_len, NULL, + oid_len + ber_NULLLen); + + rc |= ber_encode_INTEGER(TRUE, NULL, &len, NULL, sizeof(version)); + offset += len; + rc |= ber_encode_BIT_STRING(TRUE, NULL, &len, NULL, sk->ulValueLen, 0); + offset += len; + if (pk) { + rc |= ber_encode_BIT_STRING(TRUE, NULL, &len2, NULL, + pk->ulValueLen + 64, 0); + rc |= ber_encode_CHOICE(TRUE, 0, NULL, &len, NULL, len2); + offset += len; + } + + if (rc != CKR_OK) { + TRACE_DEVEL("Calculate storage for sequence failed\n"); + return CKR_FUNCTION_FAILED; + } + + if (length_only == TRUE) { + rc = ber_encode_SEQUENCE(TRUE, NULL, &len, NULL, offset); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_encode_SEQUENCE failed\n"); + return rc; + } + rc = ber_encode_PrivateKeyInfo(TRUE, + NULL, data_len, + NULL, algid_len, + NULL, len); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_encode_PrivateKeyInfo failed\n"); + return rc; + } + return rc; + } + + /* Allocate storage for sequence */ + buf = (CK_BYTE *) malloc(offset); + if (!buf) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + offset = 0; + + /* Version */ + rc = ber_encode_INTEGER(FALSE, &buf2, &len, version, sizeof(version)); + if (rc != CKR_OK) { + TRACE_ERROR("ber_encode_INTEGER of version failed\n"); + goto error; + } + memcpy(buf + offset, buf2, len); + offset += len; + free(buf2); + buf2 = NULL; + + /* sk */ + rc = ber_encode_BIT_STRING(FALSE, &buf2, &len, + sk->pValue, sk->ulValueLen, 0); + if (rc != CKR_OK) { + TRACE_ERROR("ber_encode_BIT_STRING of sk failed\n"); + goto error; + } + memcpy(buf + offset, buf2, len); + offset += len; + free(buf2); + buf2 = NULL; + + /* (pk) Optional bit-string of public key */ + if (pk && pk->pValue) { + /* append rs to public key */ + pk_rs = (CK_BYTE *)malloc(pk->ulValueLen + 64); + if (!pk_rs) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + goto error; + } + + memcpy(pk_rs, pk->pValue, pk->ulValueLen); + memset(pk_rs + pk->ulValueLen, 0x30, 64); + + rc = ber_encode_BIT_STRING(FALSE, &buf3, &len2, + pk_rs, pk->ulValueLen + 64, 0); + rc |= ber_encode_CHOICE(FALSE, 0, &buf2, &len, buf3, len2); + if (rc != CKR_OK) { + TRACE_ERROR("encoding of pk value failed\n"); + goto error; + } + memcpy(buf + offset, buf2, len); + offset += len; + free(buf2); + buf2 = NULL; + } + + /* Encode sequence */ + rc = ber_encode_SEQUENCE(FALSE, &buf2, &len, buf, offset); + if (rc != CKR_OK) { + TRACE_ERROR("ber_encode_SEQUENCE failed\n"); + goto error; + } + + algid_buf = (CK_BYTE *) malloc(oid_len + ber_NULLLen); + if (!algid_buf) { + TRACE_ERROR("%s Memory allocation failed\n", __func__); + rc = CKR_HOST_MEMORY; + goto error; + } + memcpy(algid_buf, oid, oid_len); + memcpy(algid_buf + oid_len, ber_NULL, ber_NULLLen); + + rc = ber_encode_SEQUENCE(FALSE, &algid, &algid_len, algid_buf, + oid_len + ber_NULLLen); + free(algid_buf); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_encode_SEQUENCE failed with rc=0x%lx\n", __func__, rc); + goto error; + } + + rc = ber_encode_PrivateKeyInfo(FALSE, + data, data_len, + algid, algid_len, + buf2, len); + if (rc != CKR_OK) { + TRACE_ERROR("ber_encode_PrivateKeyInfo failed\n"); + } + +error: + if (buf3) + free(buf3); + if (buf2) + free(buf2); + if (buf) + free(buf); + if (algid) + free(algid); + if (pk_rs) + free(pk_rs); + + return rc; +} + +/** + * decode an IBM Kyber private key: + * + * KyberPrivateKey ::= SEQUENCE { + * version INTEGER, -- v0, reserved 0 + * sk BIT STRING, -- private key + * pk [0] IMPLICIT OPTIONAL { + * pk||rs BIT STRING -- public key (pk) concatenated with 2x32 bytes rs + * } + * } + */ +CK_RV ber_decode_IBM_KyberPrivateKey(CK_BYTE *data, + CK_ULONG data_len, + CK_ATTRIBUTE **sk, + CK_ATTRIBUTE **pk, + CK_ATTRIBUTE **value, + const struct pqc_oid **oid) +{ + CK_ATTRIBUTE *sk_attr = NULL, *pk_attr = NULL, *value_attr = NULL; + CK_BYTE *algoid = NULL; + CK_BYTE *kyber_priv_key = NULL; + CK_BYTE *buf = NULL; + CK_BYTE *tmp = NULL; + CK_ULONG offset, buf_len, field_len, len, option; + CK_RV rc; + + /* Check if this is a Kyber private key */ + rc = ber_decode_PrivateKeyInfo(data, data_len, &algoid, &len, + &kyber_priv_key); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_decode_PrivateKeyInfo failed\n"); + return rc; + } + + if (len <= ber_NULLLen || + memcmp(algoid + len - ber_NULLLen, ber_NULL, ber_NULLLen) != 0) { + TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); + return CKR_FUNCTION_FAILED; + } + len -= ber_NULLLen; + *oid = find_pqc_by_oid(kyber_oids, algoid, len); + if (*oid == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); + return CKR_FUNCTION_FAILED; + } + + /* Decode private Kyber key */ + rc = ber_decode_SEQUENCE(kyber_priv_key, &buf, &buf_len, &field_len); + if (rc != CKR_OK) + return rc; + + /* Now build the attributes */ + offset = 0; + + /* Skip the version */ + rc = ber_decode_INTEGER(buf + offset, &tmp, &len, &field_len); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_decode_INTEGER failed\n"); + goto cleanup; + } + offset += field_len; + + /* sk */ + rc = ber_decode_BIT_STRING(buf + offset, &tmp, &len, &field_len); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_decode_BIT_STRING of (sk) failed\n"); + goto cleanup; + } else { + tmp++; /* Remove unused-bits byte */ + len--; + rc = build_attribute(CKA_IBM_KYBER_SK, tmp, len, &sk_attr); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute for (sk) failed\n"); + goto cleanup; + } + offset += field_len; + } + + /* pk (optional, within choice) */ + if (offset < buf_len) { + rc = ber_decode_CHOICE(buf + offset, &tmp, &len, &field_len, &option); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_decode_BIT_STRING of (t1) failed\n"); + goto cleanup; + } + + if (option != 0x00) { + TRACE_DEVEL("ber_decode_CHOICE returned invalid option %ld\n", + option); + goto cleanup; + } + + offset += field_len - len; + + rc = ber_decode_BIT_STRING(buf + offset, &tmp, &len, &field_len); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_decode_BIT_STRING of (pk) failed\n"); + goto cleanup; + } + tmp++; /* Remove unused-bits byte */ + len--; + + if (len > 64) + len -= 64; /* Remove 'rs' */ + + rc = build_attribute(CKA_IBM_KYBER_PK, tmp, len, &pk_attr); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute for (pk) failed\n"); + goto cleanup; + } + offset += field_len; + } + + /* Check if buffer big enough */ + if (offset > buf_len) { + TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); + rc = CKR_FUNCTION_FAILED; + goto cleanup; + } + + /* Add private key as CKA_VALUE to public key (z/OS ICSF compatibility) */ + rc = ber_decode_SEQUENCE(data, &tmp, &len, &field_len); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_decode_SEQUENCE failed with rc=0x%lx\n", __func__, rc); + goto cleanup; + } + rc = build_attribute(CKA_VALUE, data, field_len, &value_attr); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute for (t1) failed\n"); + goto cleanup; + } + + *sk = sk_attr; + *pk = pk_attr; + *value = value_attr; + + return CKR_OK; + +cleanup: + + if (sk_attr) + free(sk_attr); + if (pk_attr) + free(pk_attr); + if (value_attr) + free(value_attr); + + return rc; +} + diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/attributes.c opencryptoki-3.20.0+dfsg/usr/lib/common/attributes.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/attributes.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/attributes.c 2023-02-13 09:22:42.000000000 +0100 @@ -142,6 +142,12 @@ CK_ATTRIBUTE_PTR dest; CK_ULONG dest_len; + if (orig == NULL || orig_len == 0) { + *p_dest = NULL; + *p_dest_len = 0; + return CKR_OK; + } + /* Allocate the new array */ dest_len = orig_len; dest = malloc(dest_len * sizeof(*dest)); @@ -170,6 +176,9 @@ { CK_ATTRIBUTE_PTR it; + if (attrs == NULL || attrs_len == 0) + return NULL; + for (it = attrs; it != attrs + attrs_len; it++) if (it->type == type) return it; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/buffer.c opencryptoki-3.20.0+dfsg/usr/lib/common/buffer.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/buffer.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/buffer.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,128 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ +#define _GNU_SOURCE +#include +#include +#include +#include + +#include + +#define BUFFER_INIT_SIZE (128ul) + +struct _buffer { + size_t b_size; + char *b; +}; + +p11_buffer_t *p11_buffer_new(void) +{ + p11_buffer_t *ret = malloc(sizeof(p11_buffer_t)); + if (ret == NULL) + goto err; + + ret->b_size = BUFFER_INIT_SIZE; + ret->b = calloc(BUFFER_INIT_SIZE, sizeof(char)); + + if (ret->b == NULL) + goto err_free; + + return ret; + +err_free: + free(ret); +err: + return NULL; +} + +void p11_buffer_free(p11_buffer_t *buf) +{ + free(buf->b); + free(buf); +} + +void p11_buffer_reset(p11_buffer_t *buf) +{ + memset(buf->b, 0, buf->b_size); +} + +const char *p11_buffer_char(const p11_buffer_t *buf) +{ + return (const char *) buf->b; +} + +size_t p11_buffer_size(const p11_buffer_t *buf) +{ + return buf->b_size; +} + +long p11_buffer_append_len(p11_buffer_t *buf, const char *s, size_t len) +{ + size_t new_len = strlen(buf->b) + len; + char *b_end; + + if (!s || (len == 0)) + return strlen(buf->b); + + /* extend buffer if required */ + if ((new_len + 1) > buf->b_size) { + size_t new_b_size = + (((new_len + 1) / BUFFER_INIT_SIZE) + 1) * BUFFER_INIT_SIZE; + char *new_b = realloc(buf->b, new_b_size); + + /* ENOMEM */ + if (new_b == NULL) + return -1; + + buf->b = new_b; + buf->b_size = new_b_size; + } + + /* + * workaround: the obvious way to concatenate buf->b and s with + * strncat(buf->b, s, len) is insecure, therefore do it manually. + */ + + /* copy len bytes to the end of buf->b */ + b_end = buf->b + strnlen(buf->b, buf->b_size); + memcpy(b_end, s, len); + + /* terminate with \0 */ + b_end += len; + *b_end = '\0'; + + return new_len; +} + +long p11_buffer_append(p11_buffer_t *buf, const char *s) +{ + if (!s) + return strlen(buf->b); + return p11_buffer_append_len(buf, s, strlen(s)); +} + +long p11_buffer_append_printf(p11_buffer_t *buf, const char *fmt, ...) +{ + va_list ap; + int len, rc = 0; + char *tmp = NULL; + + va_start(ap, fmt); + len = vasprintf(&tmp, fmt, ap); + va_end(ap); + + if (len < 0) + goto err; + + rc = p11_buffer_append_len(buf, tmp, len); +err: + free(tmp); + return rc; +} diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/buffer.h opencryptoki-3.20.0+dfsg/usr/lib/common/buffer.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/buffer.h 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/buffer.h 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,29 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#ifndef __BUFFER_H +#define __BUFFER_H + +#include + +typedef struct _buffer p11_buffer_t; + +p11_buffer_t *p11_buffer_new(void); +void p11_buffer_free(p11_buffer_t *buf); +void p11_buffer_reset(p11_buffer_t *buf); + +const char *p11_buffer_char(const p11_buffer_t *buf); +size_t p11_buffer_size(const p11_buffer_t *buf); + +long p11_buffer_append_len(p11_buffer_t *buf, const char *s, size_t len); +long p11_buffer_append(p11_buffer_t *buf, const char *s); +long p11_buffer_append_printf(p11_buffer_t *buf, const char *fmt, ...); + +#endif /* __BUFFER_H */ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/common.mk opencryptoki-3.20.0+dfsg/usr/lib/common/common.mk --- opencryptoki-3.18.0+dfsg/usr/lib/common/common.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/common.mk 2023-02-13 09:22:42.000000000 +0100 @@ -5,4 +5,7 @@ usr/lib/common/trace.h usr/lib/common/h_extern.h \ usr/lib/common/sw_crypt.h usr/lib/common/defs.h \ usr/lib/common/p11util.h usr/lib/common/event_client.h \ - usr/lib/common/list.h usr/lib/common/tok_specific.h + usr/lib/common/list.h usr/lib/common/tok_specific.h \ + usr/lib/common/uri_enc.h usr/lib/common/uri.h \ + usr/lib/common/buffer.h usr/lib/common/pin_prompt.h \ + usr/lib/common/pqc_defs.h diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/decr_mgr.c opencryptoki-3.20.0+dfsg/usr/lib/common/decr_mgr.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/decr_mgr.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/decr_mgr.c 2023-02-13 09:22:42.000000000 +0100 @@ -43,6 +43,8 @@ CK_RV rc; int check; CK_ULONG strength = POLICY_STRENGTH_IDX_0; + CK_GCM_PARAMS gcm_params; + CK_MECHANISM temp_mech; if (!sess) { TRACE_ERROR("Invalid function arguments.\n"); @@ -166,43 +168,6 @@ } memset(ctx->context, 0x0, sizeof(DES_CONTEXT)); break; - case CKM_CDMF_ECB: - if (mech->ulParameterLen != 0) { - TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); - rc = CKR_MECHANISM_PARAM_INVALID; - goto done; - } - // is the key type correct? - // - rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, - &keytype); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_KEY_TYPE for the key.\n"); - goto done; - } - - if (keytype != CKK_CDMF) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_TYPE_INCONSISTENT)); - rc = CKR_KEY_TYPE_INCONSISTENT; - goto done; - } - - // Check FCV - // - // if ((nv_FCV.FunctionCntlBytes[DES_FUNCTION_BYTE] - // & FCV_CDMF_DES) == 0) - // rc = CKR_MECHANISM_INVALID; - // goto done; - - ctx->context_len = sizeof(DES_CONTEXT); - ctx->context = (CK_BYTE *) malloc(sizeof(DES_CONTEXT)); - if (!ctx->context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto done; - } - memset(ctx->context, 0x0, sizeof(DES_CONTEXT)); - break; case CKM_DES_CBC: case CKM_DES_CBC_PAD: if (mech->ulParameterLen != DES_BLOCK_SIZE || @@ -242,38 +207,6 @@ } memset(ctx->context, 0x0, sizeof(DES_CONTEXT)); break; - case CKM_CDMF_CBC: - case CKM_CDMF_CBC_PAD: - if (mech->ulParameterLen != DES_BLOCK_SIZE || - mech->pParameter == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); - rc = CKR_MECHANISM_PARAM_INVALID; - goto done; - } - // is the key type correct? - // - rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, - &keytype); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_KEY_TYPE for the key.\n"); - goto done; - } - - if (keytype != CKK_CDMF) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_TYPE_INCONSISTENT)); - rc = CKR_KEY_TYPE_INCONSISTENT; - goto done; - } - - ctx->context_len = sizeof(DES_CONTEXT); - ctx->context = (CK_BYTE *) malloc(sizeof(DES_CONTEXT)); - if (!ctx->context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto done; - } - memset(ctx->context, 0x0, sizeof(DES_CONTEXT)); - break; case CKM_DES_CFB8: case CKM_DES_CFB64: case CKM_DES_OFB64: @@ -528,13 +461,23 @@ memset(ctx->context, 0x0, sizeof(AES_CONTEXT)); break; case CKM_AES_GCM: - if (mech->ulParameterLen != sizeof(CK_GCM_PARAMS) || + if ((mech->ulParameterLen != sizeof(CK_GCM_PARAMS) && + mech->ulParameterLen != sizeof(CK_GCM_PARAMS_COMPAT)) || mech->pParameter == NULL) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); rc = CKR_MECHANISM_PARAM_INVALID; goto done; } + if (mech->ulParameterLen == sizeof(CK_GCM_PARAMS_COMPAT)) { + aes_gcm_param_from_compat((CK_GCM_PARAMS_COMPAT *)mech->pParameter, + &gcm_params); + temp_mech.mechanism = mech->mechanism; + temp_mech.pParameter = &gcm_params; + temp_mech.ulParameterLen = sizeof(gcm_params); + mech = &temp_mech; + } + rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, &keytype); if (rc != CKR_OK) { @@ -603,6 +546,36 @@ } memset(ctx->context, 0x0, sizeof(AES_CONTEXT)); break; + case CKM_AES_XTS: + if (mech->ulParameterLen != AES_INIT_VECTOR_SIZE || + mech->pParameter == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); + rc = CKR_MECHANISM_PARAM_INVALID; + goto done; + } + + rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, + &keytype); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find CKA_KEY_TYPE for the key.\n"); + goto done; + } + + if (keytype != CKK_AES_XTS) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_TYPE_INCONSISTENT)); + rc = CKR_KEY_TYPE_INCONSISTENT; + goto done; + } + + ctx->context_len = sizeof(AES_XTS_CONTEXT); + ctx->context = (CK_BYTE *) malloc(sizeof(AES_XTS_CONTEXT)); + if (!ctx->context) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + goto done; + } + memset(ctx->context, 0x0, sizeof(AES_XTS_CONTEXT)); + break; default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); rc = CKR_MECHANISM_INVALID; @@ -626,6 +599,7 @@ (CK_GCM_PARAMS *)ptr); if (rc != CKR_OK) { TRACE_ERROR("aes_gcm_dup_param failed\n"); + free(ptr); goto done; } break; @@ -741,18 +715,15 @@ return CKR_OPERATION_ACTIVE; } switch (ctx->mech.mechanism) { - case CKM_CDMF_ECB: case CKM_DES_ECB: return des_ecb_decrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); - case CKM_CDMF_CBC: case CKM_DES_CBC: return des_cbc_decrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); case CKM_DES_CBC_PAD: - case CKM_CDMF_CBC_PAD: return des_cbc_pad_decrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, @@ -814,7 +785,6 @@ return rsa_x509_decrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); -#ifndef NOAES case CKM_AES_CBC: return aes_cbc_decrypt(tokdata, sess, length_only, ctx, @@ -854,7 +824,10 @@ ctx, in_data, in_data_len, out_data, out_data_len, 0x10); -#endif + case CKM_AES_XTS: + return aes_xts_decrypt(tokdata, sess, length_only, ctx, + in_data, in_data_len, + out_data, out_data_len); default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); return CKR_MECHANISM_INVALID; @@ -901,20 +874,17 @@ } switch (ctx->mech.mechanism) { - case CKM_CDMF_ECB: case CKM_DES_ECB: return des_ecb_decrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); - case CKM_CDMF_CBC: case CKM_DES_CBC: return des_cbc_decrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); case CKM_DES_CBC_PAD: - case CKM_CDMF_CBC_PAD: return des_cbc_pad_decrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, @@ -967,7 +937,6 @@ ctx, in_data, in_data_len, out_data, out_data_len); -#ifndef NOAES case CKM_AES_ECB: return aes_ecb_decrypt_update(tokdata, sess, length_only, ctx, @@ -1012,7 +981,10 @@ ctx, in_data, in_data_len, out_data, out_data_len, 0x10); -#endif + case CKM_AES_XTS: + return aes_xts_decrypt_update(tokdata, sess, length_only, ctx, + in_data, in_data_len, + out_data, out_data_len); default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_INVALID)); return CKR_MECHANISM_INVALID; @@ -1051,16 +1023,13 @@ } switch (ctx->mech.mechanism) { - case CKM_CDMF_ECB: case CKM_DES_ECB: return des_ecb_decrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); - case CKM_CDMF_CBC: case CKM_DES_CBC: return des_cbc_decrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); case CKM_DES_CBC_PAD: - case CKM_CDMF_CBC_PAD: return des_cbc_pad_decrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); case CKM_DES_OFB64: @@ -1099,7 +1068,6 @@ case CKM_DES3_CBC_PAD: return des3_cbc_pad_decrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); -#ifndef NOAES case CKM_AES_ECB: return aes_ecb_decrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); @@ -1127,7 +1095,9 @@ case CKM_AES_GCM: return aes_gcm_decrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); -#endif + case CKM_AES_XTS: + return aes_xts_decrypt_final(tokdata, sess, length_only, + ctx, out_data, out_data_len); default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_INVALID)); return CKR_MECHANISM_INVALID; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/defs.h opencryptoki-3.20.0+dfsg/usr/lib/common/defs.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/defs.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/defs.h 2023-02-13 09:22:42.000000000 +0100 @@ -155,8 +155,10 @@ unsigned int dev_ctx_offs; }; +#if !(NOMD2) #define MD2_HASH_SIZE 16 #define MD2_BLOCK_SIZE 48 +#endif #define MD5_HASH_SIZE 16 #define MD5_BLOCK_SIZE 64 diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/dig_mgr.c opencryptoki-3.20.0+dfsg/usr/lib/common/dig_mgr.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/dig_mgr.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/dig_mgr.c 2023-02-13 09:22:42.000000000 +0100 @@ -79,6 +79,7 @@ return rc; } break; +#if !(NOMD2) case CKM_MD2: if (mech->ulParameterLen != 0) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); @@ -93,6 +94,7 @@ } memset(ctx->context, 0x0, sizeof(MD2_CONTEXT)); break; +#endif case CKM_MD5: if (mech->ulParameterLen != 0) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/encr_mgr.c opencryptoki-3.20.0+dfsg/usr/lib/common/encr_mgr.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/encr_mgr.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/encr_mgr.c 2023-02-13 09:22:42.000000000 +0100 @@ -45,6 +45,8 @@ CK_RV rc; int check; CK_ULONG strength = POLICY_STRENGTH_IDX_0; + CK_GCM_PARAMS gcm_params; + CK_MECHANISM temp_mech; if (!sess || !ctx || !mech) { TRACE_ERROR("Invalid function arguments.\n"); @@ -168,36 +170,6 @@ } memset(ctx->context, 0x0, sizeof(DES_CONTEXT)); break; - case CKM_CDMF_ECB: - if (mech->ulParameterLen != 0) { - TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); - rc = CKR_MECHANISM_PARAM_INVALID; - goto done; - } - // is the key type correct? - // - rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, - &keytype); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_KEY_TYPE for the key.\n"); - goto done; - } - - if (keytype != CKK_CDMF) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_TYPE_INCONSISTENT)); - rc = CKR_KEY_TYPE_INCONSISTENT; - goto done; - } - - ctx->context_len = sizeof(DES_CONTEXT); - ctx->context = (CK_BYTE *) malloc(sizeof(DES_CONTEXT)); - if (!ctx->context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto done; - } - memset(ctx->context, 0x0, sizeof(DES_CONTEXT)); - break; case CKM_DES_CBC: case CKM_DES_CBC_PAD: if (mech->ulParameterLen != DES_BLOCK_SIZE || @@ -269,38 +241,6 @@ } memset(ctx->context, 0x0, sizeof(DES_CONTEXT)); break; - case CKM_CDMF_CBC: - case CKM_CDMF_CBC_PAD: - if (mech->ulParameterLen != DES_BLOCK_SIZE || - mech->pParameter == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); - rc = CKR_MECHANISM_PARAM_INVALID; - goto done; - } - // is the key type correct? - // - rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, - &keytype); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_KEY_TYPE for the key.\n"); - goto done; - } - - if (keytype != CKK_CDMF) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_TYPE_INCONSISTENT)); - rc = CKR_KEY_TYPE_INCONSISTENT; - goto done; - } - - ctx->context_len = sizeof(DES_CONTEXT); - ctx->context = (CK_BYTE *) malloc(sizeof(DES_CONTEXT)); - if (!ctx->context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto done; - } - memset(ctx->context, 0x0, sizeof(DES_CONTEXT)); - break; case CKM_DES3_ECB: if (mech->ulParameterLen != 0) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); @@ -523,13 +463,23 @@ memset(ctx->context, 0x0, sizeof(AES_CONTEXT)); break; case CKM_AES_GCM: - if (mech->ulParameterLen != sizeof(CK_GCM_PARAMS) || + if ((mech->ulParameterLen != sizeof(CK_GCM_PARAMS) && + mech->ulParameterLen != sizeof(CK_GCM_PARAMS_COMPAT)) || mech->pParameter == NULL) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); rc = CKR_MECHANISM_PARAM_INVALID; goto done; } + if (mech->ulParameterLen == sizeof(CK_GCM_PARAMS_COMPAT)) { + aes_gcm_param_from_compat((CK_GCM_PARAMS_COMPAT *)mech->pParameter, + &gcm_params); + temp_mech.mechanism = mech->mechanism; + temp_mech.pParameter = &gcm_params; + temp_mech.ulParameterLen = sizeof(gcm_params); + mech = &temp_mech; + } + rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, &keytype); if (rc != CKR_OK) { @@ -598,6 +548,36 @@ } memset(ctx->context, 0x0, sizeof(AES_CONTEXT)); break; + case CKM_AES_XTS: + if (mech->ulParameterLen != AES_INIT_VECTOR_SIZE || + mech->pParameter == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); + rc = CKR_MECHANISM_PARAM_INVALID; + goto done; + } + + rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, + &keytype); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find CKA_KEY_TYPE for the key.\n"); + goto done; + } + + if (keytype != CKK_AES_XTS) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_TYPE_INCONSISTENT)); + rc = CKR_KEY_TYPE_INCONSISTENT; + goto done; + } + + ctx->context_len = sizeof(AES_XTS_CONTEXT); + ctx->context = (CK_BYTE *) malloc(sizeof(AES_XTS_CONTEXT)); + if (!ctx->context) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + goto done; + } + memset(ctx->context, 0x0, sizeof(AES_XTS_CONTEXT)); + break; default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); rc = CKR_MECHANISM_INVALID; @@ -621,6 +601,7 @@ (CK_GCM_PARAMS *)ptr); if (rc != CKR_OK) { TRACE_ERROR("aes_gcm_dup_param failed\n"); + free(ptr); goto done; } break; @@ -736,18 +717,15 @@ return CKR_OPERATION_ACTIVE; } switch (ctx->mech.mechanism) { - case CKM_CDMF_ECB: case CKM_DES_ECB: return pk_des_ecb_encrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); - case CKM_CDMF_CBC: case CKM_DES_CBC: return pk_des_cbc_encrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); case CKM_DES_CBC_PAD: - case CKM_CDMF_CBC_PAD: return des_cbc_pad_encrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); @@ -805,7 +783,6 @@ return rsa_x509_encrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); -#ifndef NOAES case CKM_AES_CBC: return aes_cbc_encrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, @@ -844,7 +821,10 @@ return aes_cfb_encrypt(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len, 0x10); -#endif + case CKM_AES_XTS: + return aes_xts_encrypt(tokdata, sess, length_only, ctx, + in_data, in_data_len, + out_data, out_data_len); default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); return CKR_MECHANISM_INVALID; @@ -891,18 +871,15 @@ } switch (ctx->mech.mechanism) { - case CKM_CDMF_ECB: case CKM_DES_ECB: return des_ecb_encrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); - case CKM_CDMF_CBC: case CKM_DES_CBC: return des_cbc_encrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); case CKM_DES_CBC_PAD: - case CKM_CDMF_CBC_PAD: return des_cbc_pad_encrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); @@ -948,7 +925,6 @@ return des3_cbc_pad_encrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len); -#ifndef NOAES case CKM_AES_ECB: return aes_ecb_encrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, @@ -985,7 +961,10 @@ return aes_cfb_encrypt_update(tokdata, sess, length_only, ctx, in_data, in_data_len, out_data, out_data_len, 0x10); -#endif + case CKM_AES_XTS: + return aes_xts_encrypt_update(tokdata, sess, length_only, ctx, + in_data, in_data_len, + out_data, out_data_len); default: return CKR_MECHANISM_INVALID; } @@ -1023,16 +1002,13 @@ return CKR_OPERATION_ACTIVE; } switch (ctx->mech.mechanism) { - case CKM_CDMF_ECB: case CKM_DES_ECB: return des_ecb_encrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); - case CKM_CDMF_CBC: case CKM_DES_CBC: return des_cbc_encrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); case CKM_DES_CBC_PAD: - case CKM_CDMF_CBC_PAD: return des_cbc_pad_encrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); case CKM_DES_OFB64: @@ -1071,7 +1047,6 @@ case CKM_DES3_CBC_PAD: return des3_cbc_pad_encrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); -#ifndef NOAES case CKM_AES_ECB: return aes_ecb_encrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len); @@ -1099,7 +1074,9 @@ case CKM_AES_CFB128: return aes_cfb_encrypt_final(tokdata, sess, length_only, ctx, out_data, out_data_len, 0x10); -#endif + case CKM_AES_XTS: + return aes_xts_encrypt_final(tokdata, sess, length_only, + ctx, out_data, out_data_len); default: return CKR_MECHANISM_INVALID; } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/event_client.c opencryptoki-3.20.0+dfsg/usr/lib/common/event_client.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/event_client.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/event_client.c 2023-02-13 09:22:42.000000000 +0100 @@ -110,7 +110,7 @@ * Returns a file descriptor representing the connection, or a negative errno * in case of an error. */ -int init_event_client() +int init_event_client(void) { int fd; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/event_client.h opencryptoki-3.20.0+dfsg/usr/lib/common/event_client.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/event_client.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/event_client.h 2023-02-13 09:22:42.000000000 +0100 @@ -27,7 +27,7 @@ unsigned long nothandled_replies; }; -int init_event_client(); +int init_event_client(void); int send_event(int fd, unsigned int type, unsigned int flags, unsigned int payload_len, const char *payload, diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/globals.c opencryptoki-3.20.0+dfsg/usr/lib/common/globals.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/globals.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/globals.c 2023-02-13 09:22:42.000000000 +0100 @@ -27,6 +27,7 @@ #include "defs.h" #include "host_defs.h" #include "h_extern.h" +#include "pqc_oids.h" struct ST_FCN_LIST function_list; @@ -39,10 +40,10 @@ { 0x06, 0x07, 0x2a, 0x86, 0x48, 0xce, 0x3d, 0x02, 0x01 }; const CK_BYTE ber_rsaEncryption[] = { 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x01 }; +#if !(NOMD2) const CK_BYTE ber_md2WithRSAEncryption[] = { 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x02 }; -const CK_BYTE ber_md4WithRSAEncryption[] = - { 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x03 }; +#endif const CK_BYTE ber_md5WithRSAEncryption[] = { 0x06, 0x09, 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x01, 0x04 }; const CK_BYTE ber_sha1WithRSAEncryption[] = @@ -54,10 +55,12 @@ // Algorithm IDs. (Sequence of OID plus parms, usually NULL) // +#if !(NOMD2) const CK_BYTE ber_AlgMd2[] = { 0x30, 0x0C, 0x06, 0x08, 0x2A, 0x86, 0x48, 0x86, 0xF7, 0x0D, 0x02, 0x02, 0x05, 0x00 }; +#endif const CK_BYTE ber_AlgMd5[] = { 0x30, 0x0C, 0x06, 0x08, 0x2A, 0x86, 0x48, @@ -102,25 +105,24 @@ const CK_BYTE der_AlgIdECBase[] = { 0x30, 0x09, 0x06, 0x07, 0x2A, 0x86, 0x48, 0xCE, 0x3D, 0x02, 0x01 }; -const CK_BYTE ber_AlgIdDilithium[] = - { 0x30, 0x0F, 0x06, 0x0B, 0x2B, 0x06, 0x01, - 0x04, 0x01, 0x02, 0x82, 0x0B, 0x01, 0x06, - 0x05, 0x05, 0x00 -}; +const CK_BYTE ber_NULL[] = { 0x05, 0x00 }; // ID Lengths // const CK_ULONG ber_idDSALen = sizeof(ber_idDSA); const CK_ULONG ber_idECLen = sizeof(ber_idEC); const CK_ULONG ber_rsaEncryptionLen = sizeof(ber_rsaEncryption); +#if !(NOMD2) const CK_ULONG ber_md2WithRSAEncryptionLen = sizeof(ber_md2WithRSAEncryption); -const CK_ULONG ber_md4WithRSAEncryptionLen = sizeof(ber_md4WithRSAEncryption); +#endif const CK_ULONG ber_md5WithRSAEncryptionLen = sizeof(ber_md5WithRSAEncryption); const CK_ULONG ber_sha1WithRSAEncryptionLen = sizeof(ber_sha1WithRSAEncryption); const CK_ULONG ber_idDHLen = sizeof(ber_idDH); const CK_ULONG ber_idDilithiumLen = sizeof(ber_idDilithium); +#if !(NOMD2) const CK_ULONG ber_AlgMd2Len = sizeof(ber_AlgMd2); +#endif const CK_ULONG ber_AlgMd5Len = sizeof(ber_AlgMd5); const CK_ULONG ber_AlgSha1Len = sizeof(ber_AlgSha1); const CK_ULONG ber_AlgSha224Len = sizeof(ber_AlgSha224); @@ -129,7 +131,7 @@ const CK_ULONG ber_AlgSha512Len = sizeof(ber_AlgSha512); const CK_ULONG ber_AlgIdRSAEncryptionLen = sizeof(ber_AlgIdRSAEncryption); const CK_ULONG der_AlgIdECBaseLen = sizeof(der_AlgIdECBase); -const CK_ULONG ber_AlgIdDilithiumLen = sizeof(ber_AlgIdDilithium); +const CK_ULONG ber_NULLLen = sizeof(ber_NULL); const CK_ULONG des_weak_count = 4; const CK_ULONG des_semi_weak_count = 12; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/h_extern.h opencryptoki-3.20.0+dfsg/usr/lib/common/h_extern.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/h_extern.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/h_extern.h 2023-02-13 09:22:42.000000000 +0100 @@ -26,6 +26,7 @@ #include #include "dlist.h" #include "host_defs.h" +#include "pqc_defs.h" #include @@ -56,27 +57,27 @@ extern const CK_ULONG ber_rsaEncryptionLen; extern const CK_BYTE der_AlgIdECBase[]; extern const CK_ULONG der_AlgIdECBaseLen; -extern const CK_BYTE ber_AlgIdDilithium[]; -extern const CK_ULONG ber_AlgIdDilithiumLen; extern const CK_BYTE ber_idDSA[]; extern const CK_ULONG ber_idDSALen; extern const CK_BYTE ber_idDH[]; extern const CK_ULONG ber_idDHLen; extern const CK_BYTE ber_idEC[]; extern const CK_ULONG ber_idECLen; -extern const CK_BYTE ber_idDilithium[]; -extern const CK_ULONG ber_idDilithiumLen; +extern const CK_BYTE ber_NULL[]; +extern const CK_ULONG ber_NULLLen; +#if !(NOMD2) extern const CK_BYTE ber_md2WithRSAEncryption[]; extern const CK_ULONG ber_md2WithRSAEncryptionLen; -extern const CK_BYTE ber_md4WithRSAEncryption[]; -extern const CK_ULONG ber_md4WithRSAEncryptionLen; +#endif extern const CK_BYTE ber_md5WithRSAEncryption[]; extern const CK_ULONG ber_md5WithRSAEncryptionLen; extern const CK_BYTE ber_sha1WithRSAEncryption[]; extern const CK_ULONG ber_sha1WithRSAEncryptionLen; +#if !(NOMD2) extern const CK_BYTE ber_AlgMd2[]; extern const CK_ULONG ber_AlgMd2Len; +#endif extern const CK_BYTE ber_AlgMd5[]; extern const CK_ULONG ber_AlgMd5Len; extern const CK_BYTE ber_AlgSha1[]; @@ -411,12 +412,6 @@ CK_RV dp_x9dh_validate_attribute(TEMPLATE *tmpl, CK_ATTRIBUTE *attr, CK_ULONG mode); -CK_RV communicate(CK_ULONG cmd_id, - CK_VOID_PTR pReq, CK_ULONG req_len, - CK_VOID_PTR pRep, CK_ULONG_PTR repl_len, - CK_BYTE_PTR pOut, CK_ULONG out_len, - CK_BYTE_PTR pIn, CK_ULONG in_len); - CK_RV save_token_object(STDLL_TokData_t *tokdata, OBJECT *obj); CK_RV save_private_token_object(STDLL_TokData_t *tokdata, OBJECT *obj); CK_RV save_public_token_object(STDLL_TokData_t *tokdata, OBJECT *obj); @@ -985,7 +980,6 @@ // DES mechanisms // CK_RV ckm_des_key_gen(STDLL_TokData_t *tokdata, TEMPLATE *tmpl); -CK_RV ckm_cdmf_key_gen(STDLL_TokData_t *tokdata, TEMPLATE *tmpl); CK_RV ckm_des_ecb_encrypt(STDLL_TokData_t *tokdata, CK_BYTE *in_data, CK_ULONG in_data_len, @@ -1342,6 +1336,16 @@ CK_BYTE *in_data, CK_ULONG in_data_len, CK_BYTE *out_data, CK_ULONG *out_data_len); +CK_RV aes_xts_encrypt_update(STDLL_TokData_t *tokdata, SESSION *sess, + CK_BBOOL length_only, ENCR_DECR_CONTEXT *context, + CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len); + +CK_RV aes_xts_decrypt_update(STDLL_TokData_t *tokdata, SESSION *sess, + CK_BBOOL length_only, ENCR_DECR_CONTEXT *context, + CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len); + CK_RV aes_ecb_encrypt_final(STDLL_TokData_t *tokdata, SESSION *sess, CK_BBOOL length_only, ENCR_DECR_CONTEXT *context, CK_BYTE *out_data, CK_ULONG *out_data_len); @@ -1376,6 +1380,14 @@ CK_BBOOL length_only, ENCR_DECR_CONTEXT *context, CK_BYTE *out_data, CK_ULONG *out_data_len); +CK_RV aes_xts_encrypt_final(STDLL_TokData_t *tokdata, SESSION *sess, + CK_BBOOL length_only, ENCR_DECR_CONTEXT *context, + CK_BYTE *out_data, CK_ULONG *out_data_len); + +CK_RV aes_xts_decrypt_final(STDLL_TokData_t *tokdata, SESSION *sess, + CK_BBOOL length_only, ENCR_DECR_CONTEXT *context, + CK_BYTE *out_data, CK_ULONG *out_data_len); + CK_RV aes_mac_sign(STDLL_TokData_t *tokdata, SESSION *sess, CK_BBOOL length_only, SIGN_VERIFY_CONTEXT *ctx, CK_BYTE *in_data, CK_ULONG in_data_len, @@ -1431,7 +1443,7 @@ // AES mechanisms // -CK_RV ckm_aes_key_gen(STDLL_TokData_t *, TEMPLATE *tmpl); +CK_RV ckm_aes_key_gen(STDLL_TokData_t *, TEMPLATE *tmpl, CK_BBOOL xts); CK_RV ckm_aes_ecb_encrypt(STDLL_TokData_t *, CK_BYTE *in_data, CK_ULONG in_data_len, CK_BYTE *out_data, @@ -1460,6 +1472,25 @@ CK_ULONG in_data_len, CK_BYTE *out_data, CK_ULONG *out_data_len, CK_BYTE *counterblock, CK_ULONG counter_width, OBJECT *key); +CK_RV ckm_aes_xts_crypt(STDLL_TokData_t *tokdata, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, + CK_ULONG *out_data_len, + CK_BYTE *tweak, OBJECT *key, + CK_BBOOL initial, CK_BBOOL final, + CK_BYTE *iv, CK_BBOOL encrypt); + +CK_RV aes_xts_cipher(CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len, + CK_BYTE *tweak, CK_BOOL encrypt, CK_BBOOL initial, + CK_BBOOL final, CK_BYTE* iv, + CK_RV (*iv_from_tweak)(CK_BYTE *tweak, CK_BYTE* iv, + void * cb_data), + CK_RV (*cipher_blocks)(CK_BYTE *in, CK_BYTE *out, + CK_ULONG len, CK_BYTE *iv, + void * cb_data), + void *cb_data); CK_RV ckm_aes_wrap_format(STDLL_TokData_t *, CK_BBOOL length_only, CK_BYTE **data, CK_ULONG *data_len); @@ -1493,6 +1524,9 @@ CK_RV aes_gcm_free_param(CK_GCM_PARAMS *params); +void aes_gcm_param_from_compat(const CK_GCM_PARAMS_COMPAT *from, + CK_GCM_PARAMS *to); + CK_RV aes_ofb_encrypt(STDLL_TokData_t *tokdata, SESSION *sess, CK_BBOOL length_only, ENCR_DECR_CONTEXT *ctx, CK_BYTE *in_data, @@ -1559,6 +1593,20 @@ CK_BBOOL length_only, ENCR_DECR_CONTEXT *ctx, CK_BYTE *out_data, CK_ULONG *out_data_len, CK_ULONG cfb_len); +CK_RV aes_xts_encrypt(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len); +CK_RV aes_xts_decrypt(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len); // SHA mechanisms // @@ -1619,6 +1667,7 @@ //adding the hmac secret key generation here CK_RV ckm_generic_secret_key_gen(STDLL_TokData_t *tokdata, TEMPLATE *tmpl); +#if !(NOMD2) // MD2 mechanisms // CK_RV md2_hash(STDLL_TokData_t *tokdata, SESSION *sess, CK_BBOOL length_only, @@ -1656,6 +1705,7 @@ void ckm_md2_transform(STDLL_TokData_t *tokdata, CK_BYTE *state, CK_BYTE *checksum, CK_BYTE *block); +#endif // MD5 mechanisms @@ -2067,7 +2117,7 @@ CK_BBOOL session_mgr_user_session_exists(STDLL_TokData_t *tokdata); CK_BBOOL session_mgr_public_session_exists(STDLL_TokData_t *tokdata); -CK_RV session_mgr_get_op_state(SESSION *sess, +CK_RV session_mgr_get_op_state(STDLL_TokData_t *tokdata, SESSION *sess, CK_BBOOL length_only, CK_BYTE *data, CK_ULONG *data_len); @@ -2075,6 +2125,8 @@ CK_OBJECT_HANDLE encr_key, CK_OBJECT_HANDLE auth_key, CK_BYTE *data, CK_ULONG data_len); +CK_RV session_mgr_cancel(STDLL_TokData_t *tokdata, SESSION *sess, + CK_FLAGS flags); CK_BBOOL pin_expired(CK_SESSION_INFO *, CK_FLAGS); CK_BBOOL pin_locked(CK_SESSION_INFO *, CK_FLAGS); void set_login_flags(CK_USER_TYPE, CK_FLAGS_32 *); @@ -2095,6 +2147,8 @@ void object_mgr_add_to_shm(OBJECT *obj, LW_SHM_TYPE *shm); CK_RV object_mgr_del_from_shm(OBJECT *obj, LW_SHM_TYPE *shm); +CK_RV object_mgr_get_shm_entry_for_obj(STDLL_TokData_t *tokdata, OBJECT *obj, + TOK_OBJ_ENTRY **entry); CK_RV object_mgr_check_shm(STDLL_TokData_t *tokdata, OBJECT *obj); CK_RV object_mgr_search_shm_for_obj(TOK_OBJ_ENTRY *list, CK_ULONG lo, @@ -2231,7 +2285,7 @@ CK_ULONG mode, CK_ULONG class, CK_ULONG subclass, OBJECT **key); -CK_RV object_copy(STDLL_TokData_t *tokdata, +CK_RV object_copy(STDLL_TokData_t *tokdata, SESSION *sess, CK_ATTRIBUTE *pTemplate, CK_ULONG ulCount, OBJECT *old_obj, OBJECT **new_obj); @@ -2250,7 +2304,7 @@ OBJECT **obj, CK_BBOOL replace, int data_size, const char *fname); -CK_RV object_set_attribute_values(STDLL_TokData_t *tokdata, +CK_RV object_set_attribute_values(STDLL_TokData_t *tokdata, SESSION *sess, OBJECT *obj, CK_ATTRIBUTE *pTemplate, CK_ULONG ulCount); @@ -2498,9 +2552,48 @@ CK_RV ibm_dilithium_priv_wrap_get_data(TEMPLATE *tmpl, CK_BBOOL length_only, CK_BYTE **data, CK_ULONG *data_len); CK_RV ibm_dilithium_priv_unwrap(TEMPLATE *tmpl, CK_BYTE *data, - CK_ULONG total_length); + CK_ULONG total_length, CK_BBOOL add_value); CK_RV ibm_dilithium_priv_unwrap_get_data(TEMPLATE *tmpl, - CK_BYTE *data, CK_ULONG total_length); + CK_BYTE *data, CK_ULONG total_length, + CK_BBOOL add_value); + +// Kyber routines +// +CK_RV ibm_kyber_publ_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); +CK_RV ibm_kyber_publ_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); +CK_RV ibm_kyber_publ_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, + CK_ATTRIBUTE *attr, CK_ULONG mode); +CK_RV ibm_kyber_publ_get_spki(TEMPLATE *tmpl, CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len); +CK_RV ibm_kyber_priv_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); +CK_RV ibm_kyber_priv_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); +CK_RV ibm_kyber_priv_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, + CK_ATTRIBUTE *attr, CK_ULONG mode); +CK_RV ibm_kyber_priv_wrap_get_data(TEMPLATE *tmpl, CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len); +CK_RV ibm_kyber_priv_unwrap(TEMPLATE *tmpl, CK_BYTE *data, + CK_ULONG total_length, CK_BBOOL add_value); +CK_RV ibm_kyber_priv_unwrap_get_data(TEMPLATE *tmpl, + CK_BYTE *data, CK_ULONG total_length, + CK_BBOOL add_value); + +// PQC helper routines +// +CK_RV ibm_pqc_publ_get_spki(TEMPLATE *tmpl, CK_KEY_TYPE keytype, + CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len); +CK_RV ibm_pqc_priv_wrap_get_data(TEMPLATE *tmpl, CK_KEY_TYPE keytype, + CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len); +CK_RV ibm_pqc_priv_unwrap(TEMPLATE *tmpl, CK_KEY_TYPE keytype, CK_BYTE *data, + CK_ULONG total_length, CK_BBOOL add_value); +CK_RV ibm_pqc_priv_unwrap_get_data(TEMPLATE *tmpl, CK_KEY_TYPE keytype, + CK_BYTE *data, CK_ULONG total_length, + CK_BBOOL add_value); +const struct pqc_oid *ibm_pqc_get_keyform_mode(TEMPLATE *tmpl, + CK_MECHANISM_TYPE mech); +CK_RV ibm_pqc_add_keyform_mode(TEMPLATE *tmpl, const struct pqc_oid *oid, + CK_MECHANISM_TYPE mech); // diffie-hellman routines // @@ -2522,19 +2615,6 @@ CK_BYTE *data, CK_ULONG total_length); CK_RV dh_priv_unwrap(TEMPLATE *tmpl, CK_BYTE *data, CK_ULONG data_len); -// KEA routines -// -CK_RV kea_publ_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV kea_publ_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV kea_publ_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); -CK_BBOOL kea_priv_check_exportability(CK_ATTRIBUTE_TYPE type); -CK_RV kea_priv_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV kea_priv_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV kea_priv_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - - // Generic secret key routines CK_RV generic_secret_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); CK_RV generic_secret_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); @@ -2546,24 +2626,6 @@ CK_RV generic_secret_unwrap(TEMPLATE *tmpl, CK_BYTE *data, CK_ULONG data_len, CK_BBOOL fromend); -// RC2 routines -CK_RV rc2_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV rc2_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV rc2_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// RC4 routines -CK_RV rc4_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV rc4_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV rc4_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// RC5 routines -CK_RV rc5_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV rc5_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV rc5_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - // DES routines CK_RV des_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); CK_BBOOL des_check_weak_key(CK_BYTE *key); @@ -2593,63 +2655,15 @@ // AES routines CK_RV aes_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV aes_set_default_attributes(TEMPLATE *tmpl, TEMPLATE *basetmpl, CK_ULONG mode); +CK_RV aes_set_default_attributes(TEMPLATE *tmpl, TEMPLATE *basetmpl, + CK_ULONG mode, CK_BBOOL xts); CK_RV aes_unwrap(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, CK_BYTE *data, - CK_ULONG data_len, CK_BBOOL fromend); + CK_ULONG data_len, CK_BBOOL fromend, CK_BBOOL xts); CK_RV aes_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); + CK_ATTRIBUTE *attr, CK_ULONG mode, CK_BBOOL xts); CK_RV aes_wrap_get_data(TEMPLATE *tmpl, CK_BBOOL length_only, CK_BYTE **data, CK_ULONG *data_len); -// CAST routines -CK_RV cast_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV cast_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV cast_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// CAST3 routines -CK_RV cast3_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV cast3_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV cast3_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// CAST5 routines -CK_RV cast5_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV cast5_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV cast5_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// IDEA routines -CK_RV idea_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV idea_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV idea_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// CDMF routines -CK_RV cdmf_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV cdmf_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV cdmf_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// SKIPJACK routines -CK_RV skipjack_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV skipjack_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV skipjack_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// BATON routines -CK_RV baton_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV baton_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV baton_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - -// JUNIPER routines -CK_RV juniper_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV juniper_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode); -CK_RV juniper_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode); - - // modular math routines // CK_RV mp_subtract(CK_BYTE *bigint, CK_ULONG val, CK_ULONG len); @@ -2818,35 +2832,66 @@ CK_ATTRIBUTE **pub_key, CK_ATTRIBUTE **priv_key); -CK_RV ber_encode_IBM_DilithiumPublicKey(CK_BBOOL length_only, CK_BYTE **data, - CK_ULONG *data_len, CK_ATTRIBUTE *rho, - CK_ATTRIBUTE *t1); +CK_RV ber_encode_IBM_DilithiumPublicKey(CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len, + const CK_BYTE *oid, CK_ULONG oid_len, + CK_ATTRIBUTE *rho, CK_ATTRIBUTE *t1); CK_RV ber_decode_IBM_DilithiumPublicKey(CK_BYTE *data, - CK_ULONG data_len, - CK_ATTRIBUTE **rho_attr, - CK_ATTRIBUTE **t1_attr); + CK_ULONG data_len, + CK_ATTRIBUTE **rho_attr, + CK_ATTRIBUTE **t1_attr, + CK_ATTRIBUTE **value_attr, + const struct pqc_oid **oid); CK_RV ber_encode_IBM_DilithiumPrivateKey(CK_BBOOL length_only, - CK_BYTE **data, - CK_ULONG *data_len, - CK_ATTRIBUTE *rho, - CK_ATTRIBUTE *seed, - CK_ATTRIBUTE *tr, - CK_ATTRIBUTE *s1, - CK_ATTRIBUTE *s2, - CK_ATTRIBUTE *t0, - CK_ATTRIBUTE *t1); + CK_BYTE **data, + CK_ULONG *data_len, + const CK_BYTE *oid, CK_ULONG oid_len, + CK_ATTRIBUTE *rho, + CK_ATTRIBUTE *seed, + CK_ATTRIBUTE *tr, + CK_ATTRIBUTE *s1, + CK_ATTRIBUTE *s2, + CK_ATTRIBUTE *t0, + CK_ATTRIBUTE *t1); CK_RV ber_decode_IBM_DilithiumPrivateKey(CK_BYTE *data, - CK_ULONG data_len, - CK_ATTRIBUTE **rho, - CK_ATTRIBUTE **seed, - CK_ATTRIBUTE **tr, - CK_ATTRIBUTE **s1, - CK_ATTRIBUTE **s2, - CK_ATTRIBUTE **t0, - CK_ATTRIBUTE **t1); + CK_ULONG data_len, + CK_ATTRIBUTE **rho, + CK_ATTRIBUTE **seed, + CK_ATTRIBUTE **tr, + CK_ATTRIBUTE **s1, + CK_ATTRIBUTE **s2, + CK_ATTRIBUTE **t0, + CK_ATTRIBUTE **t1, + CK_ATTRIBUTE **value, + const struct pqc_oid **oid); + +CK_RV ber_encode_IBM_KyberPublicKey(CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len, + const CK_BYTE *oid, CK_ULONG oid_len, + CK_ATTRIBUTE *pk); + +CK_RV ber_decode_IBM_KyberPublicKey(CK_BYTE *data, + CK_ULONG data_len, + CK_ATTRIBUTE **pk_attr, + CK_ATTRIBUTE **value_attr, + const struct pqc_oid **oid); + +CK_RV ber_encode_IBM_KyberPrivateKey(CK_BBOOL length_only, + CK_BYTE **data, + CK_ULONG *data_len, + const CK_BYTE *oid, CK_ULONG oid_len, + CK_ATTRIBUTE *sk, + CK_ATTRIBUTE *pk); + +CK_RV ber_decode_IBM_KyberPrivateKey(CK_BYTE *data, + CK_ULONG data_len, + CK_ATTRIBUTE **sk, + CK_ATTRIBUTE **pk, + CK_ATTRIBUTE **value, + const struct pqc_oid **oid); typedef CK_RV (*t_rsa_encrypt)(STDLL_TokData_t *, CK_BYTE *in_data, CK_ULONG in_data_len, CK_BYTE *out_data, @@ -2995,6 +3040,12 @@ CK_RV openssl_specific_aes_cmac(STDLL_TokData_t *tokdata, CK_BYTE *message, CK_ULONG message_len, OBJECT *key, CK_BYTE *mac, CK_BBOOL first, CK_BBOOL last, CK_VOID_PTR *ctx); +CK_RV openssl_specific_aes_xts(STDLL_TokData_t *tokdata, + CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len, + OBJECT *key_obj, CK_BYTE *tweak, + CK_BOOL encrypt, CK_BBOOL initial, + CK_BBOOL final, CK_BYTE* iv); CK_RV openssl_specific_des_ecb(STDLL_TokData_t *tokdata, CK_BYTE *in_data, diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/host_defs.h opencryptoki-3.20.0+dfsg/usr/lib/common/host_defs.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/host_defs.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/host_defs.h 2023-02-13 09:22:42.000000000 +0100 @@ -119,6 +119,13 @@ CK_BBOOL cbc_pad; } AES_CONTEXT; +typedef struct _AES_XTS_CONTEXT { + CK_BYTE iv[AES_INIT_VECTOR_SIZE]; + CK_BYTE data[2 * AES_BLOCK_SIZE]; + CK_ULONG len; + CK_BBOOL initialized; +} AES_XTS_CONTEXT; + typedef struct _AES_DATA_CONTEXT { CK_BYTE data[AES_BLOCK_SIZE]; CK_ULONG len; @@ -147,14 +154,14 @@ typedef SHA1_CONTEXT SHA2_CONTEXT; - +#if !(NOMD2) typedef struct _MD2_CONTEXT { CK_BYTE state[16]; // state CK_BYTE checksum[16]; // checksum CK_ULONG count; // number of bytes, modulo 16 CK_BYTE buffer[16]; // input buffer } MD2_CONTEXT; - +#endif typedef struct _MD5_CONTEXT { CK_ULONG i[2]; // number of _bits_ handled mod 2^64 @@ -228,6 +235,9 @@ typedef struct _OP_STATE_DATA { + CK_CHAR library_version[16]; /* zero termination does not matter here */ + CK_CHAR manufacturerID[member_size(CK_TOKEN_INFO_32, manufacturerID)]; + CK_CHAR model[member_size(CK_TOKEN_INFO_32, model)]; CK_STATE session_state; CK_ULONG active_operation; CK_ULONG data_len; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/kdf_translation.c opencryptoki-3.20.0+dfsg/usr/lib/common/kdf_translation.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/kdf_translation.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/kdf_translation.c 2023-02-13 09:22:42.000000000 +0100 @@ -55,6 +55,36 @@ return CKR_OK; } return CKR_FUNCTION_FAILED; + case 19: + if (strcmp("CKD_IBM_HYBRID_NULL", str) == 0) { + *kdf = CKD_IBM_HYBRID_NULL; + return CKR_OK; + } + return CKR_FUNCTION_FAILED; + case 23: + if (strcmp("CKD_IBM_HYBRID_SHA1_KDF", str) == 0) { + *kdf = CKD_IBM_HYBRID_SHA1_KDF; + return CKR_OK; + } + return CKR_FUNCTION_FAILED; + case 25: + if (strcmp("CKD_IBM_HYBRID_SHA224_KDF", str) == 0) { + *kdf = CKD_IBM_HYBRID_SHA224_KDF; + return CKR_OK; + } + if (strcmp("CKD_IBM_HYBRID_SHA256_KDF", str) == 0) { + *kdf = CKD_IBM_HYBRID_SHA256_KDF; + return CKR_OK; + } + if (strcmp("CKD_IBM_HYBRID_SHA384_KDF", str) == 0) { + *kdf = CKD_IBM_HYBRID_SHA384_KDF; + return CKR_OK; + } + if (strcmp("CKD_IBM_HYBRID_SHA512_KDF", str) == 0) { + *kdf = CKD_IBM_HYBRID_SHA512_KDF; + return CKR_OK; + } + return CKR_FUNCTION_FAILED; default: return CKR_FUNCTION_FAILED; } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/key.c opencryptoki-3.20.0+dfsg/usr/lib/common/key.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/key.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/key.c 2023-02-13 09:22:42.000000000 +0100 @@ -52,28 +52,10 @@ // dh_priv_validate_attribute // dh_priv_check_exportability // -// kea_publ_check_required_attributes -// kea_publ_validate_attribute -// kea_priv_check_required_attributes -// kea_priv_validate_attribute -// kea_priv_check_exportability -// // generic_secret_check_required_attributes // generic_secret_validate_attribute // generic_secret_set_default_attributes // -// rc2_check_required_attributes -// rc2_validate_attribute -// rc2_priv_check_exportability -// -// rc4_check_required_attributes -// rc4_validate_attribute -// rc4_priv_check_exportability -// -// rc5_check_required_attributes -// rc5_validate_attribute -// rc5_priv_check_exportability -// // des_check_required_attributes // des_validate_attribute // des_priv_check_exportability @@ -86,38 +68,6 @@ // des3_validate_attribute // des3_priv_check_exportability // -// cast_check_required_attributes -// cast_validate_attribute -// cast_priv_check_exportability -// -// cast3_check_required_attributes -// cast3_validate_attribute -// cast3_priv_check_exportability -// -// cast5_check_required_attributes -// cast5_validate_attribute -// cast5_priv_check_exportability -// -// idea_check_required_attributes -// idea_validate_attribute -// idea_priv_check_exportability -// -// cdmf_check_required_attributes -// cdmf_validate_attribute -// cdmf_priv_check_exportability -// -// skipjack_check_required_attributes -// skipjack_validate_attribute -// skipjack_priv_check_exportability -// -// baton_check_required_attributes -// baton_validate_attribute -// baton_priv_check_exportability -// -// juniper_check_required_attributes -// juniper_validate_attribute -// juniper_priv_check_exportability -// #include #include @@ -131,6 +81,7 @@ #include "h_extern.h" #include "attributes.h" #include "trace.h" +#include "pqc_defs.h" #include "tok_spec_struct.h" @@ -771,6 +722,9 @@ case CKK_IBM_PQC_DILITHIUM: rc = ibm_dilithium_publ_get_spki(tmpl, length_only, data, data_len); break; + case CKK_IBM_PQC_KYBER: + rc = ibm_kyber_publ_get_spki(tmpl, length_only, data, data_len); + break; default: TRACE_ERROR("%s\n", ock_err(ERR_KEY_TYPE_INCONSISTENT)); return CKR_KEY_TYPE_INCONSISTENT; @@ -1100,7 +1054,10 @@ rc = ec_priv_unwrap(tmpl, data, data_len); break; case CKK_IBM_PQC_DILITHIUM: - rc = ibm_dilithium_priv_unwrap(tmpl, data, data_len); + rc = ibm_dilithium_priv_unwrap(tmpl, data, data_len, TRUE); + break; + case CKK_IBM_PQC_KYBER: + rc = ibm_kyber_priv_unwrap(tmpl, data, data_len, TRUE); break; default: TRACE_ERROR("%s\n", ock_err(ERR_WRAPPED_KEY_INVALID)); @@ -1697,7 +1654,6 @@ CK_RV rc; switch (keytype) { - case CKK_CDMF: case CKK_DES: rc = des_unwrap(tokdata, tmpl, data, data_len, fromend); break; @@ -1705,15 +1661,11 @@ rc = des3_unwrap(tokdata, tmpl, data, data_len, fromend); break; case CKK_AES: - rc = aes_unwrap(tokdata, tmpl, data, data_len, fromend); + case CKK_AES_XTS: + rc = aes_unwrap(tokdata, tmpl, data, data_len, fromend, + keytype == CKK_AES_XTS); break; case CKK_GENERIC_SECRET: - case CKK_RC2: - case CKK_RC4: - case CKK_RC5: - case CKK_CAST: - case CKK_CAST3: - case CKK_CAST5: rc = generic_secret_unwrap(tmpl, data, data_len, fromend); break; default: @@ -2710,6 +2662,117 @@ return rc; } +static CK_RV ibm_pqc_keyform_mode_attrs_by_mech(CK_MECHANISM_TYPE mech, + CK_ATTRIBUTE_TYPE *keyform_attr, + CK_ATTRIBUTE_TYPE *mode_attr, + const struct pqc_oid **oids) +{ + switch (mech) { + case CKM_IBM_DILITHIUM: + *keyform_attr = CKA_IBM_DILITHIUM_KEYFORM; + *mode_attr = CKA_IBM_DILITHIUM_MODE; + *oids = dilithium_oids; + break; + case CKM_IBM_KYBER: + *keyform_attr = CKA_IBM_KYBER_KEYFORM; + *mode_attr = CKA_IBM_KYBER_MODE; + *oids = kyber_oids; + break; + default: + TRACE_ERROR("Unsupported mechanims: 0x%lx\n", mech); + return CKR_MECHANISM_INVALID; + } + + return CKR_OK; +} + +const struct pqc_oid *ibm_pqc_get_keyform_mode(TEMPLATE *tmpl, + CK_MECHANISM_TYPE mech) +{ + CK_ATTRIBUTE *attr = NULL; + const struct pqc_oid *oids = NULL, *oid; + CK_ATTRIBUTE_TYPE keyform_attr = 0; + CK_ATTRIBUTE_TYPE mode_attr = 0; + + if (ibm_pqc_keyform_mode_attrs_by_mech(mech, &keyform_attr, + &mode_attr, &oids) != CKR_OK) + return NULL; + + if (template_attribute_find(tmpl, keyform_attr, &attr) && + attr->ulValueLen == sizeof(CK_ULONG) && attr->pValue != NULL) { + oid = find_pqc_by_keyform(oids, *(CK_ULONG *)(attr->pValue)); + if (oid == NULL) { + TRACE_ERROR("KEYFORM attribute specifies an invalid value: %lu\n", + *(CK_ULONG *)(attr->pValue)); + return NULL; + } + return oid; + } + + if (template_attribute_find(tmpl, mode_attr, &attr) && + attr->ulValueLen != 0 && attr->pValue != NULL) { + oid = find_pqc_by_oid(oids, attr->pValue, attr->ulValueLen); + if (oid == NULL) { + TRACE_ERROR("MODE attribute specifies an invalid value\n"); + return NULL; + } + return oid; + } + + TRACE_ERROR("Neither KEYFORM nor MODE found\n"); + return NULL; +} + +CK_RV ibm_pqc_add_keyform_mode(TEMPLATE *tmpl, const struct pqc_oid *oid, + CK_MECHANISM_TYPE mech) +{ + CK_ATTRIBUTE *mode = NULL; + CK_ATTRIBUTE *keyform = NULL; + CK_RV rc; + CK_ATTRIBUTE_TYPE keyform_attr = 0; + CK_ATTRIBUTE_TYPE mode_attr = 0; + const struct pqc_oid *oids; + + if (ibm_pqc_keyform_mode_attrs_by_mech(mech, &keyform_attr, + &mode_attr, &oids) != CKR_OK) + return CKR_MECHANISM_INVALID; + + rc = build_attribute(mode_attr, (CK_BYTE *)oid->oid, oid->oid_len, &mode); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute failed\n"); + goto error; + } + rc = template_update_attribute(tmpl, mode); + if (rc != CKR_OK) { + TRACE_DEVEL("template_update_attribute failed.\n"); + goto error; + } + mode = NULL; + + rc = build_attribute(keyform_attr, (CK_BYTE *)&oid->keyform, + sizeof(CK_ULONG), &keyform); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute failed\n"); + goto error; + } + rc = template_update_attribute(tmpl, keyform); + if (rc != CKR_OK) { + TRACE_DEVEL("template_update_attribute failed.\n"); + goto error; + } + keyform = NULL; + + return CKR_OK; + +error: + if (mode) + free(mode); + if (keyform) + free(keyform); + + return rc; +} + /* * Extract the SubjectPublicKeyInfo from the Dilithium public key */ @@ -2718,21 +2781,12 @@ { CK_ATTRIBUTE *rho = NULL; CK_ATTRIBUTE *t1 = NULL; - CK_ULONG keyform; + const struct pqc_oid *oid; CK_RV rc; - rc = template_attribute_get_ulong(tmpl, CKA_IBM_DILITHIUM_KEYFORM, - &keyform); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_IBM_DILITHIUM_KEYFORM for the key.\n"); - return rc; - } - - if ( keyform != IBM_DILITHIUM_KEYFORM_ROUND2) { - TRACE_ERROR("This key has an unexpected CKA_IBM_DILITHIUM_KEYFORM: " - "%ld \n", keyform); - return CKR_ATTRIBUTE_VALUE_INVALID; - } + oid = ibm_pqc_get_keyform_mode(tmpl, CKM_IBM_DILITHIUM); + if (oid == NULL) + return CKR_TEMPLATE_INCOMPLETE; rc = template_attribute_get_non_empty(tmpl, CKA_IBM_DILITHIUM_RHO, &rho); if (rc != CKR_OK) { @@ -2745,7 +2799,9 @@ return rc; } - rc = ber_encode_IBM_DilithiumPublicKey(length_only, data,data_len, rho, t1); + rc = ber_encode_IBM_DilithiumPublicKey(length_only, data, data_len, + oid->oid, oid->oid_len, + rho, t1); if (rc != CKR_OK) { TRACE_ERROR("ber_encode_IBM_DilithiumPublicKey failed.\n"); return rc; @@ -2762,23 +2818,12 @@ CK_ATTRIBUTE *rho = NULL, *seed = NULL; CK_ATTRIBUTE *tr = NULL, *s1 = NULL, *s2 = NULL; CK_ATTRIBUTE *t0 = NULL, *t1 = NULL; - CK_ULONG keyform; + const struct pqc_oid *oid; CK_RV rc; - /* A private Dilithium key must have a keyform value */ - rc = template_attribute_get_ulong(tmpl, CKA_IBM_DILITHIUM_KEYFORM, - &keyform); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_IBM_DILITHIUM_KEYFORM for the key.\n"); - return rc; - } - - /* Check if it's an expected keyform */ - if (keyform != IBM_DILITHIUM_KEYFORM_ROUND2) { - TRACE_ERROR("This key has an unexpected CKA_IBM_DILITHIUM_KEYFORM: %ld\n", - keyform); - return CKR_ATTRIBUTE_VALUE_INVALID; - } + oid = ibm_pqc_get_keyform_mode(tmpl, CKM_IBM_DILITHIUM); + if (oid == NULL) + return CKR_TEMPLATE_INCOMPLETE; rc = template_attribute_get_non_empty(tmpl, CKA_IBM_DILITHIUM_RHO, &rho); if (rc != CKR_OK) { @@ -2823,7 +2868,8 @@ } rc = ber_encode_IBM_DilithiumPrivateKey(length_only, data, data_len, - rho, seed, tr, s1, s2, t0, t1); + oid->oid, oid->oid_len, + rho, seed, tr, s1, s2, t0, t1); if (rc != CKR_OK) { TRACE_DEVEL("ber_encode_IBM_DilithiumPrivateKey failed\n"); } @@ -2832,18 +2878,28 @@ } CK_RV ibm_dilithium_priv_unwrap_get_data(TEMPLATE *tmpl, CK_BYTE *data, - CK_ULONG total_length) + CK_ULONG total_length, + CK_BBOOL add_value) { CK_ATTRIBUTE *rho = NULL; CK_ATTRIBUTE *t1 = NULL; + CK_ATTRIBUTE *value = NULL; + const struct pqc_oid *oid; CK_RV rc; - rc = ber_decode_IBM_DilithiumPublicKey(data, total_length, &rho, &t1); + rc = ber_decode_IBM_DilithiumPublicKey(data, total_length, &rho, &t1, + &value, &oid); if (rc != CKR_OK) { TRACE_ERROR("ber_decode_DilithiumPublicKey failed\n"); return rc; } + rc = ibm_pqc_add_keyform_mode(tmpl, oid, CKM_IBM_DILITHIUM); + if (rc != CKR_OK) { + TRACE_ERROR("ibm_pqc_add_keyform_mode failed\n"); + goto error; + } + rc = template_update_attribute(tmpl, rho); if (rc != CKR_OK) { TRACE_DEVEL("template_update_attribute failed.\n"); @@ -2856,6 +2912,16 @@ goto error; } t1 = NULL; + if (add_value) { + rc = template_update_attribute(tmpl, value); + if (rc != CKR_OK) { + TRACE_DEVEL("template_update_attribute failed.\n"); + goto error; + } + } else { + free(value); + } + value = NULL; return CKR_OK; @@ -2864,6 +2930,8 @@ free(rho); if (t1) free(t1); + if (value) + free(value); return rc; } @@ -2871,19 +2939,27 @@ // // CK_RV ibm_dilithium_priv_unwrap(TEMPLATE *tmpl, CK_BYTE *data, - CK_ULONG total_length) + CK_ULONG total_length, CK_BBOOL add_value) { - CK_ATTRIBUTE *rho = NULL, *seed = NULL, *tr = NULL; + CK_ATTRIBUTE *rho = NULL, *seed = NULL, *tr = NULL, *value = NULL; CK_ATTRIBUTE *s1 = NULL, *s2 = NULL, *t0 = NULL, *t1 = NULL; + const struct pqc_oid *oid; CK_RV rc; rc = ber_decode_IBM_DilithiumPrivateKey(data, total_length, - &rho, &seed, &tr, &s1, &s2, &t0, &t1); + &rho, &seed, &tr, &s1, &s2, &t0, + &t1, &value, &oid); if (rc != CKR_OK) { TRACE_ERROR("der_decode_IBM_DilithiumPrivateKey failed\n"); return rc; } + rc = ibm_pqc_add_keyform_mode(tmpl, oid, CKM_IBM_DILITHIUM); + if (rc != CKR_OK) { + TRACE_ERROR("ibm_pqc_add_keyform_mode failed\n"); + goto error; + } + rc = template_update_attribute(tmpl, rho); if (rc != CKR_OK) { TRACE_ERROR("template_update_attribute failed\n"); @@ -2928,6 +3004,16 @@ } } t1 = NULL; + if (add_value) { + rc = template_update_attribute(tmpl, value); + if (rc != CKR_OK) { + TRACE_DEVEL("template_update_attribute failed.\n"); + goto error; + } + } else { + free(value); + } + value = NULL; return CKR_OK; @@ -2946,10 +3032,246 @@ free(t0); if (t1) free(t1); + if (value) + free(value); + + return rc; +} + +/* + * Extract the SubjectPublicKeyInfo from the Kyber public key + */ +CK_RV ibm_kyber_publ_get_spki(TEMPLATE *tmpl, CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len) +{ + CK_ATTRIBUTE *pk = NULL; + const struct pqc_oid *oid; + CK_RV rc; + + oid = ibm_pqc_get_keyform_mode(tmpl, CKM_IBM_KYBER); + if (oid == NULL) + return CKR_TEMPLATE_INCOMPLETE; + + rc = template_attribute_get_non_empty(tmpl, CKA_IBM_KYBER_PK, &pk); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find CKA_IBM_KYBER_PK for the key.\n"); + return rc; + } + + rc = ber_encode_IBM_KyberPublicKey(length_only, data, data_len, + oid->oid, oid->oid_len, pk); + if (rc != CKR_OK) { + TRACE_ERROR("ber_encode_IBM_KyberPublicKey failed.\n"); + return rc; + } + + return CKR_OK; +} + + +CK_RV ibm_kyber_priv_wrap_get_data(TEMPLATE *tmpl, + CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len) +{ + CK_ATTRIBUTE *sk = NULL, *pk = NULL; + const struct pqc_oid *oid; + CK_RV rc; + + oid = ibm_pqc_get_keyform_mode(tmpl, CKM_IBM_KYBER); + if (oid == NULL) + return CKR_TEMPLATE_INCOMPLETE; + + rc = template_attribute_get_non_empty(tmpl, CKA_IBM_KYBER_SK, &sk); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find CKA_IBM_KYBER_SK for the key.\n"); + return rc; + } + + rc = template_attribute_get_non_empty(tmpl, CKA_IBM_KYBER_PK, &pk); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find CKA_IBM_KYBER_PK for the key.\n"); + return rc; + } + + rc = ber_encode_IBM_KyberPrivateKey(length_only, data, data_len, + oid->oid, oid->oid_len, sk, pk); + if (rc != CKR_OK) { + TRACE_DEVEL("ber_encode_IBM_KyberPrivateKey failed\n"); + } return rc; } +CK_RV ibm_kyber_priv_unwrap_get_data(TEMPLATE *tmpl, CK_BYTE *data, + CK_ULONG total_length, + CK_BBOOL add_value) +{ + CK_ATTRIBUTE *pk = NULL; + CK_ATTRIBUTE *value = NULL; + const struct pqc_oid *oid; + CK_RV rc; + + rc = ber_decode_IBM_KyberPublicKey(data, total_length, &pk, + &value, &oid); + if (rc != CKR_OK) { + TRACE_ERROR("ber_decode_IBM_KyberPublicKey failed\n"); + return rc; + } + + rc = ibm_pqc_add_keyform_mode(tmpl, oid, CKM_IBM_KYBER); + if (rc != CKR_OK) { + TRACE_ERROR("ibm_pqc_add_keyform_mode failed\n"); + goto error; + } + + rc = template_update_attribute(tmpl, pk); + if (rc != CKR_OK) { + TRACE_DEVEL("template_update_attribute failed.\n"); + goto error; + } + pk = NULL; + if (add_value) { + rc = template_update_attribute(tmpl, value); + if (rc != CKR_OK) { + TRACE_DEVEL("template_update_attribute failed.\n"); + goto error; + } + } else { + free(value); + } + value = NULL; + + return CKR_OK; + +error: + if (pk) + free(pk); + if (value) + free(value); + + return rc; +} + +// +// +CK_RV ibm_kyber_priv_unwrap(TEMPLATE *tmpl, CK_BYTE *data, + CK_ULONG total_length, CK_BBOOL add_value) +{ + CK_ATTRIBUTE *sk = NULL, *pk = NULL, *value = NULL; + const struct pqc_oid *oid; + CK_RV rc; + + rc = ber_decode_IBM_KyberPrivateKey(data, total_length, + &sk, &pk, &value, &oid); + if (rc != CKR_OK) { + TRACE_ERROR("ber_decode_IBM_KyberPrivateKey failed\n"); + return rc; + } + + rc = ibm_pqc_add_keyform_mode(tmpl, oid, CKM_IBM_KYBER); + if (rc != CKR_OK) { + TRACE_ERROR("ibm_pqc_add_keyform_mode failed\n"); + goto error; + } + + rc = template_update_attribute(tmpl, sk); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + sk = NULL; + rc = template_update_attribute(tmpl, pk); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + pk = NULL; + if (add_value) { + rc = template_update_attribute(tmpl, value); + if (rc != CKR_OK) { + TRACE_DEVEL("template_update_attribute failed.\n"); + goto error; + } + } else { + free(value); + } + value = NULL; + + return CKR_OK; + +error: + if (sk) + free(sk); + if (pk) + free(pk); + if (value) + free(value); + + return rc; +} + +CK_RV ibm_pqc_publ_get_spki(TEMPLATE *tmpl, CK_KEY_TYPE keytype, + CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len) +{ + switch (keytype) { + case CKK_IBM_PQC_DILITHIUM: + return ibm_dilithium_publ_get_spki(tmpl, length_only, data, data_len); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_publ_get_spki(tmpl, length_only, data, data_len); + default: + TRACE_DEVEL("Key type 0x%lx not supported.\n", keytype); + return CKR_KEY_TYPE_INCONSISTENT; + } +} + +CK_RV ibm_pqc_priv_wrap_get_data(TEMPLATE *tmpl, CK_KEY_TYPE keytype, + CK_BBOOL length_only, + CK_BYTE **data, CK_ULONG *data_len) +{ + switch (keytype) { + case CKK_IBM_PQC_DILITHIUM: + return ibm_dilithium_priv_wrap_get_data(tmpl, length_only, data, + data_len); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_priv_wrap_get_data(tmpl, length_only, data, data_len); + default: + TRACE_DEVEL("Key type 0x%lx not supported.\n", keytype); + return CKR_KEY_TYPE_INCONSISTENT; + } +} + +CK_RV ibm_pqc_priv_unwrap(TEMPLATE *tmpl, CK_KEY_TYPE keytype, CK_BYTE *data, + CK_ULONG total_length, CK_BBOOL add_value) +{ + switch (keytype) { + case CKK_IBM_PQC_DILITHIUM: + return ibm_dilithium_priv_unwrap(tmpl, data, total_length, add_value); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_priv_unwrap(tmpl, data, total_length, add_value); + default: + TRACE_DEVEL("Key type 0x%lx not supported.\n", keytype); + return CKR_KEY_TYPE_INCONSISTENT; + } +} + +CK_RV ibm_pqc_priv_unwrap_get_data(TEMPLATE *tmpl, CK_KEY_TYPE keytype, + CK_BYTE *data, CK_ULONG total_length, + CK_BBOOL add_value) +{ + switch (keytype) { + case CKK_IBM_PQC_DILITHIUM: + return ibm_dilithium_priv_unwrap_get_data(tmpl, data, total_length, + add_value); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_priv_unwrap_get_data(tmpl, data, total_length, + add_value); + default: + TRACE_DEVEL("Key type 0x%lx not supported.\n", keytype); + return CKR_KEY_TYPE_INCONSISTENT; + } +} + // dsa_publ_check_required_attributes() // CK_RV dsa_publ_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) @@ -3706,7 +4028,7 @@ { switch (attr->type) { case CKA_ECDSA_PARAMS: - if (mode == MODE_CREATE || mode == MODE_KEYGEN) + if (mode == MODE_CREATE || mode == MODE_KEYGEN || mode == MODE_DERIVE) return CKR_OK; TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); @@ -3918,7 +4240,7 @@ { switch (attr->type) { case CKA_ECDSA_PARAMS: - if (mode == MODE_CREATE) + if (mode == MODE_CREATE || mode == MODE_DERIVE) return CKR_OK; TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); @@ -3994,12 +4316,7 @@ } rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &point); if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_EC_POINT for the key.\n"); - return rc; - } - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &point); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find EC Point for the key.\n"); + TRACE_ERROR("Could not find CKA_VALUE for the key.\n"); return rc; } @@ -4569,6 +4886,7 @@ p11_attribute_trim(prime); p11_attribute_trim(base); p11_attribute_trim(value); + num_bits = value->ulValueLen * 8; rc = template_update_attribute(tmpl, prime); if (rc != CKR_OK) { @@ -4675,356 +4993,6 @@ return rc; } - -// kea_publ_check_required_attributes() -// -CK_RV kea_publ_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_PRIME, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE || mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_PRIME\n"); - return rc; - } - } - - rc = template_attribute_get_non_empty(tmpl, CKA_SUBPRIME, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE || mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_SUBPRIME\n"); - return rc; - } - } - - rc = template_attribute_get_non_empty(tmpl, CKA_BASE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE || mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_BASE\n"); - return rc; - } - } - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - return publ_key_check_required_attributes(tmpl, mode); -} - - -// kea_publ_set_default_attributes() -// -CK_RV kea_publ_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *prime_attr = NULL; - CK_ATTRIBUTE *subprime_attr = NULL; - CK_ATTRIBUTE *base_attr = NULL; - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_RV rc; - - if (mode) - prime_attr = NULL; - - - publ_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - prime_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - subprime_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - base_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - - if (!type_attr || !prime_attr || !subprime_attr || !base_attr - || !value_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - prime_attr->type = CKA_PRIME; - prime_attr->ulValueLen = 0; - prime_attr->pValue = NULL; - - subprime_attr->type = CKA_SUBPRIME; - subprime_attr->ulValueLen = 0; - subprime_attr->pValue = NULL; - - base_attr->type = CKA_BASE; - base_attr->ulValueLen = 0; - base_attr->pValue = NULL; - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_KEA; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, prime_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - prime_attr = NULL; - rc = template_update_attribute(tmpl, subprime_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - subprime_attr = NULL; - rc = template_update_attribute(tmpl, base_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - base_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (prime_attr) - free(prime_attr); - if (subprime_attr) - free(subprime_attr); - if (base_attr) - free(base_attr); - if (value_attr) - free(value_attr); - - return rc; -} - - -// kea_publ_validate_attribute() -// -CK_RV kea_publ_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_PRIME: - case CKA_SUBPRIME: - case CKA_BASE: - if (mode == MODE_CREATE || mode == MODE_KEYGEN) { - p11_attribute_trim(attr); - return CKR_OK; - } - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - case CKA_VALUE: - if (mode == MODE_CREATE) { - p11_attribute_trim(attr); - return CKR_OK; - } - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - default: - return publ_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// kea_priv_check_required_attributes() -// -CK_RV kea_priv_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_PRIME, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_PRIME\n"); - return rc; - } - } - - rc = template_attribute_get_non_empty(tmpl, CKA_SUBPRIME, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_SUBPRIME\n"); - return rc; - } - } - - rc = template_attribute_get_non_empty(tmpl, CKA_BASE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_BASE\n"); - return rc; - } - } - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - return priv_key_check_required_attributes(tmpl, mode); -} - - -// kea_priv_set_default_attributes() -// -CK_RV kea_priv_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *prime_attr = NULL; - CK_ATTRIBUTE *subprime_attr = NULL; - CK_ATTRIBUTE *base_attr = NULL; - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_RV rc; - - if (mode) - prime_attr = NULL; - - priv_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - prime_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - subprime_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - base_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - - if (!type_attr || !prime_attr || !base_attr || !value_attr - || !subprime_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - prime_attr->type = CKA_PRIME; - prime_attr->ulValueLen = 0; - prime_attr->pValue = NULL; - - subprime_attr->type = CKA_SUBPRIME; - subprime_attr->ulValueLen = 0; - subprime_attr->pValue = NULL; - - base_attr->type = CKA_BASE; - base_attr->ulValueLen = 0; - base_attr->pValue = NULL; - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_KEA; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, prime_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - prime_attr = NULL; - rc = template_update_attribute(tmpl, subprime_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - subprime_attr = NULL; - rc = template_update_attribute(tmpl, base_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - base_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (prime_attr) - free(prime_attr); - if (subprime_attr) - free(subprime_attr); - if (base_attr) - free(base_attr); - if (value_attr) - free(value_attr); - - return rc; -} - - -// kea_priv_validate_attribute() -// -CK_RV kea_priv_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_PRIME: - case CKA_SUBPRIME: - case CKA_BASE: - case CKA_VALUE: - if (mode == MODE_CREATE) { - p11_attribute_trim(attr); - return CKR_OK; - } - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - default: - return priv_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// kea_priv_check_exportability() -// -CK_BBOOL kea_priv_check_exportability(CK_ATTRIBUTE_TYPE type) -{ - switch (type) { - case CKA_VALUE: - return FALSE; - } - - return TRUE; -} - // ibm_dilithium_publ_set_default_attributes() // CK_RV ibm_dilithium_publ_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) @@ -5032,17 +5000,17 @@ CK_ATTRIBUTE *type_attr = NULL; CK_ATTRIBUTE *rho_attr = NULL; CK_ATTRIBUTE *t1_attr = NULL; - CK_ATTRIBUTE *keyform_attr = NULL; + CK_ATTRIBUTE *value_attr = NULL; CK_RV rc; publ_key_set_default_attributes(tmpl, mode); type_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - keyform_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_ULONG)); rho_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); t1_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); + value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - if (!type_attr || !rho_attr || !t1_attr || !keyform_attr) { + if (!type_attr || !rho_attr || !t1_attr || !value_attr) { TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); rc = CKR_HOST_MEMORY; goto error; @@ -5053,11 +5021,6 @@ type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); *(CK_KEY_TYPE *) type_attr->pValue = CKK_IBM_PQC_DILITHIUM; - keyform_attr->type = CKA_IBM_DILITHIUM_KEYFORM; - keyform_attr->ulValueLen = sizeof(CK_ULONG); - keyform_attr->pValue = (CK_BYTE *) keyform_attr + sizeof(CK_ATTRIBUTE); - *(CK_ULONG *) keyform_attr->pValue = IBM_DILITHIUM_KEYFORM_ROUND2; - rho_attr->type = CKA_IBM_DILITHIUM_RHO; rho_attr->ulValueLen = 0; rho_attr->pValue = NULL; @@ -5066,6 +5029,10 @@ t1_attr->ulValueLen = 0; t1_attr->pValue = NULL; + value_attr->type = CKA_VALUE; + value_attr->ulValueLen = 0; + value_attr->pValue = NULL; + rc = template_update_attribute(tmpl, type_attr); if (rc != CKR_OK) { TRACE_ERROR("template_update_attribute failed\n"); @@ -5084,12 +5051,12 @@ goto error; } t1_attr = NULL; - rc = template_update_attribute(tmpl, keyform_attr); + rc = template_update_attribute(tmpl, value_attr); if (rc != CKR_OK) { TRACE_ERROR("template_update_attribute failed\n"); goto error; } - keyform_attr = NULL; + value_attr = NULL; return CKR_OK; @@ -5100,8 +5067,8 @@ free(rho_attr); if (t1_attr) free(t1_attr); - if (keyform_attr) - free(keyform_attr); + if (value_attr) + free(value_attr); return rc; } @@ -5118,13 +5085,12 @@ CK_ATTRIBUTE *s2_attr = NULL; CK_ATTRIBUTE *t0_attr = NULL; CK_ATTRIBUTE *t1_attr = NULL; - CK_ATTRIBUTE *keyform_attr = NULL; + CK_ATTRIBUTE *value_attr = NULL; CK_RV rc; priv_key_set_default_attributes(tmpl, mode); type_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - keyform_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_ULONG)); rho_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); seed_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); tr_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); @@ -5132,9 +5098,10 @@ s2_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); t0_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); t1_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); + value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); if (!type_attr || !rho_attr || !seed_attr || !tr_attr || !s1_attr - || !s2_attr || !t0_attr || !t1_attr || !keyform_attr) { + || !s2_attr || !t0_attr || !t1_attr || !value_attr) { TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); rc = CKR_HOST_MEMORY; goto error; @@ -5145,11 +5112,6 @@ type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); *(CK_KEY_TYPE *) type_attr->pValue = CKK_IBM_PQC_DILITHIUM; - keyform_attr->type = CKA_IBM_DILITHIUM_KEYFORM; - keyform_attr->ulValueLen = sizeof(CK_ULONG); - keyform_attr->pValue = (CK_BYTE *) keyform_attr + sizeof(CK_ATTRIBUTE); - *(CK_ULONG *) keyform_attr->pValue = IBM_DILITHIUM_KEYFORM_ROUND2; - rho_attr->type = CKA_IBM_DILITHIUM_RHO; rho_attr->ulValueLen = 0; rho_attr->pValue = NULL; @@ -5178,18 +5140,16 @@ t1_attr->ulValueLen = 0; t1_attr->pValue = NULL; + value_attr->type = CKA_VALUE; + value_attr->ulValueLen = 0; + value_attr->pValue = NULL; + rc = template_update_attribute(tmpl, type_attr); if (rc != CKR_OK) { TRACE_ERROR("template_update_attribute failed\n"); goto error; } type_attr = NULL; - rc = template_update_attribute(tmpl, keyform_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - keyform_attr = NULL; rc = template_update_attribute(tmpl, rho_attr); if (rc != CKR_OK) { TRACE_ERROR("template_update_attribute failed\n"); @@ -5232,6 +5192,12 @@ goto error; } t1_attr = NULL; + rc = template_update_attribute(tmpl, value_attr); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + value_attr = NULL; return CKR_OK; @@ -5252,37 +5218,265 @@ free(t0_attr); if (t1_attr) free(t1_attr); - if (keyform_attr) - free(keyform_attr); + if (value_attr) + free(value_attr); return rc; } -// ibm_dilithium_publ_check_required_attributes() +// ibm_dilithium_publ_set_default_attributes() // -CK_RV ibm_dilithium_publ_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) +CK_RV ibm_kyber_publ_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) { + CK_ATTRIBUTE *type_attr = NULL; + CK_ATTRIBUTE *pk_attr = NULL; + CK_ATTRIBUTE *value_attr = NULL; + CK_RV rc; + + publ_key_set_default_attributes(tmpl, mode); + + type_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); + pk_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); + value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); + + if (!type_attr || !pk_attr ||!value_attr) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + goto error; + } + + type_attr->type = CKA_KEY_TYPE; + type_attr->ulValueLen = sizeof(CK_KEY_TYPE); + type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); + *(CK_KEY_TYPE *) type_attr->pValue = CKK_IBM_PQC_KYBER; + + pk_attr->type = CKA_IBM_KYBER_PK; + pk_attr->ulValueLen = 0; + pk_attr->pValue = NULL; + + value_attr->type = CKA_VALUE; + value_attr->ulValueLen = 0; + value_attr->pValue = NULL; + + rc = template_update_attribute(tmpl, type_attr); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + type_attr = NULL; + rc = template_update_attribute(tmpl, pk_attr); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + pk_attr = NULL; + rc = template_update_attribute(tmpl, value_attr); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + value_attr = NULL; + + return CKR_OK; + +error: + if (type_attr) + free(type_attr); + if (pk_attr) + free(pk_attr); + if (value_attr) + free(value_attr); + + return rc; +} + +// ibm_dilithium_priv_set_default_attributes() +// +CK_RV ibm_kyber_priv_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) +{ + CK_ATTRIBUTE *type_attr = NULL; + CK_ATTRIBUTE *sk_attr = NULL; + CK_ATTRIBUTE *pk_attr = NULL; + CK_ATTRIBUTE *value_attr = NULL; + CK_RV rc; + + priv_key_set_default_attributes(tmpl, mode); + + type_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); + sk_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); + pk_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); + value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); + + if (!type_attr || !sk_attr || !pk_attr || !value_attr) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + goto error; + } + + type_attr->type = CKA_KEY_TYPE; + type_attr->ulValueLen = sizeof(CK_KEY_TYPE); + type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); + *(CK_KEY_TYPE *) type_attr->pValue = CKK_IBM_PQC_KYBER; + + sk_attr->type = CKA_IBM_KYBER_SK; + sk_attr->ulValueLen = 0; + sk_attr->pValue = NULL; + + pk_attr->type = CKA_IBM_KYBER_PK; + pk_attr->ulValueLen = 0; + pk_attr->pValue = NULL; + + value_attr->type = CKA_VALUE; + value_attr->ulValueLen = 0; + value_attr->pValue = NULL; + + rc = template_update_attribute(tmpl, type_attr); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + type_attr = NULL; + rc = template_update_attribute(tmpl, sk_attr); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + sk_attr = NULL; + rc = template_update_attribute(tmpl, pk_attr); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + pk_attr = NULL; + rc = template_update_attribute(tmpl, value_attr); + if (rc != CKR_OK) { + TRACE_ERROR("template_update_attribute failed\n"); + goto error; + } + value_attr = NULL; + + return CKR_OK; + +error: + if (type_attr) + free(type_attr); + if (sk_attr) + free(sk_attr); + if (pk_attr) + free(pk_attr); + if (value_attr) + free(value_attr); + + return rc; +} + +static CK_RV ibm_pqc_check_attributes(TEMPLATE *tmpl, CK_ULONG mode, + CK_MECHANISM_TYPE mech, + CK_ULONG *req_attrs, + CK_ULONG num_req_attrs) +{ + CK_ATTRIBUTE_TYPE keyform_attr; + CK_ATTRIBUTE_TYPE mode_attr; CK_ATTRIBUTE *attr = NULL; - static CK_ULONG req_attrs[] = { - CKA_IBM_DILITHIUM_KEYFORM, - CKA_IBM_DILITHIUM_RHO, - CKA_IBM_DILITHIUM_T1, - }; + CK_BBOOL keyform_present = FALSE; + CK_BBOOL mode_present = FALSE; + const struct pqc_oid *oids, *oid; CK_ULONG i; + CK_RV rc; - /* MODE_KEYGEN: attrs are added during keygen */ - if (mode == MODE_KEYGEN || mode == MODE_UNWRAP) - return publ_key_check_required_attributes(tmpl, mode); + if (ibm_pqc_keyform_mode_attrs_by_mech(mech, &keyform_attr, + &mode_attr, &oids) != CKR_OK) + return CKR_MECHANISM_INVALID; + + if (template_attribute_find(tmpl, keyform_attr, &attr) && + attr->ulValueLen == sizeof(CK_ULONG) && attr->pValue != NULL) { + oid = find_pqc_by_keyform(oids, *(CK_ULONG *)(attr->pValue)); + if (oid == NULL) { + TRACE_ERROR("%s, attribute KEYFORM has an unsupported value.\n", + ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); + return CKR_ATTRIBUTE_VALUE_INVALID; + } + keyform_present = TRUE; + } + + if (template_attribute_find(tmpl, mode_attr, &attr) && + attr->ulValueLen > 0 && attr->pValue != NULL) { + oid = find_pqc_by_oid(oids, attr->pValue, attr->ulValueLen); + if (oid == NULL) { + TRACE_ERROR("%s, attribute MODE has an unsupported value.\n", + ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); + return CKR_ATTRIBUTE_VALUE_INVALID; + } + mode_present = TRUE; + } - /* MODE_CREATE (key import) or MODE_COPY: check if all attrs present */ - for (i = 0; i < sizeof(req_attrs) / sizeof(req_attrs[0]); i++) { - if (!(template_attribute_find(tmpl, req_attrs[i], &attr))) { - TRACE_ERROR("%s, attribute %08lX missing.\n", - ock_err(ERR_TEMPLATE_INCOMPLETE), req_attrs[i]); + switch (mode) { + case MODE_CREATE: + /* Either CKA_VALUE or all other attrs must be present */ + if (template_attribute_find(tmpl, CKA_VALUE, &attr) && + attr->ulValueLen > 0 && attr->pValue != NULL) + break; + for (i = 0; i < num_req_attrs; i++) { + rc = template_attribute_get_non_empty(tmpl, req_attrs[i], &attr); + if (rc != CKR_OK) { + if (rc != CKR_ATTRIBUTE_VALUE_INVALID) + TRACE_ERROR("%s, attribute %08lX missing.\n", + ock_err(ERR_TEMPLATE_INCOMPLETE), req_attrs[i]); + return rc; + } + } + /* fallthrough */ + case MODE_KEYGEN: + /* Either keyform or mode or none of it must be present */ + if (keyform_present && mode_present) { + TRACE_ERROR("%s, only one of KEYFORM or MODE can be specified .\n", + ock_err(ERR_TEMPLATE_INCONSISTENT)); + return CKR_TEMPLATE_INCONSISTENT; + } + break; + case MODE_UNWRAP: + /* neither keyform or mode must be present */ + if (keyform_present || mode_present) { + TRACE_ERROR("%s, none of KEYFORM or MODE can be specified .\n", + ock_err(ERR_TEMPLATE_INCONSISTENT)); + return CKR_TEMPLATE_INCONSISTENT; + } + break; + case MODE_COPY: + /* All attributes must be present */ + if (!keyform_present || !mode_present) { + TRACE_ERROR("%s, KEYFORM or MODE must be specified .\n", + ock_err(ERR_TEMPLATE_INCOMPLETE)); return CKR_TEMPLATE_INCOMPLETE; } + for (i = 0; i < num_req_attrs; i++) { + if (!template_attribute_find(tmpl, req_attrs[i], &attr)) { + TRACE_ERROR("%s, attribute %08lX missing.\n", + ock_err(ERR_TEMPLATE_INCOMPLETE), req_attrs[i]); + return CKR_TEMPLATE_INCOMPLETE; + } + } + break; } + return CKR_OK; +} + +// ibm_dilithium_publ_check_required_attributes() +// +CK_RV ibm_dilithium_publ_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) +{ + static CK_ULONG req_attrs[] = { + CKA_IBM_DILITHIUM_RHO, + CKA_IBM_DILITHIUM_T1, + }; + CK_RV rc; + + rc = ibm_pqc_check_attributes(tmpl, mode, CKM_IBM_DILITHIUM, req_attrs, + sizeof(req_attrs) / sizeof(req_attrs[0])); + if (rc != CKR_OK) + return rc; + /* All required attrs found, check them */ return publ_key_check_required_attributes(tmpl, mode); } @@ -5291,9 +5485,7 @@ // CK_RV ibm_dilithium_priv_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) { - CK_ATTRIBUTE *attr = NULL; static CK_ULONG req_attrs[] = { - CKA_IBM_DILITHIUM_KEYFORM, CKA_IBM_DILITHIUM_RHO, CKA_IBM_DILITHIUM_SEED, CKA_IBM_DILITHIUM_TR, @@ -5302,54 +5494,123 @@ CKA_IBM_DILITHIUM_T0, CKA_IBM_DILITHIUM_T1, }; - CK_ULONG i; - - /* MODE_KEYGEN: attrs are added during keygen */ - if (mode == MODE_KEYGEN || mode == MODE_UNWRAP) - return priv_key_check_required_attributes(tmpl, mode); + CK_RV rc; - /* MODE_CREATE (key import) or MODE_COPY: check if all attrs present */ - for (i = 0; i < sizeof(req_attrs) / sizeof(req_attrs[0]); i++) { - if (!(template_attribute_find(tmpl, req_attrs[i], &attr))) { - TRACE_ERROR("%s, attribute %08lX missing.\n", - ock_err(ERR_TEMPLATE_INCOMPLETE), req_attrs[i]); - return CKR_TEMPLATE_INCOMPLETE; - } - } + rc = ibm_pqc_check_attributes(tmpl, mode, CKM_IBM_DILITHIUM, req_attrs, + sizeof(req_attrs) / sizeof(req_attrs[0])); + if (rc != CKR_OK) + return rc; /* All required attrs found, check them */ return priv_key_check_required_attributes(tmpl, mode); } -// ibm_dilithium_publ_validate_attribute() +// ibm_kyber_publ_check_required_attributes() // -CK_RV ibm_dilithium_publ_validate_attribute(STDLL_TokData_t *tokdata, - TEMPLATE *tmpl, CK_ATTRIBUTE *attr, - CK_ULONG mode) +CK_RV ibm_kyber_publ_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) { - switch (attr->type) { - case CKA_IBM_DILITHIUM_RHO: - case CKA_IBM_DILITHIUM_T1: - if (mode == MODE_CREATE) + static CK_ULONG req_attrs[] = { + CKA_IBM_KYBER_PK, + }; + CK_RV rc; + + rc = ibm_pqc_check_attributes(tmpl, mode, CKM_IBM_KYBER, req_attrs, + sizeof(req_attrs) / sizeof(req_attrs[0])); + if (rc != CKR_OK) + return rc; + + /* All required attrs found, check them */ + return publ_key_check_required_attributes(tmpl, mode); +} + +// ibm_kyber_priv_check_required_attributes() +// +CK_RV ibm_kyber_priv_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) +{ + static CK_ULONG req_attrs[] = { + CKA_IBM_KYBER_SK, + CKA_IBM_KYBER_PK, + }; + CK_RV rc; + + rc = ibm_pqc_check_attributes(tmpl, mode, CKM_IBM_KYBER, req_attrs, + sizeof(req_attrs) / sizeof(req_attrs[0])); + if (rc != CKR_OK) + return rc; + + /* All required attrs found, check them */ + return priv_key_check_required_attributes(tmpl, mode); +} + +static CK_RV ibm_pqc_validate_keyform_mode(CK_ATTRIBUTE *attr, CK_ULONG mode, + CK_MECHANISM_TYPE mech) +{ + CK_ATTRIBUTE_TYPE keyform_attr; + CK_ATTRIBUTE_TYPE mode_attr; + const struct pqc_oid *oids, *oid; + + if (ibm_pqc_keyform_mode_attrs_by_mech(mech, &keyform_attr, + &mode_attr, &oids) != CKR_OK) + return CKR_MECHANISM_INVALID; + + if (attr->type == keyform_attr) { + if (mode == MODE_CREATE || mode == MODE_KEYGEN) { + if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); + return CKR_ATTRIBUTE_VALUE_INVALID; + } + oid = find_pqc_by_keyform(oids, *((CK_ULONG *)attr->pValue)); + if (oid == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); + return CKR_ATTRIBUTE_VALUE_INVALID; + } return CKR_OK; + } TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); return CKR_ATTRIBUTE_READ_ONLY; - case CKA_IBM_DILITHIUM_KEYFORM: + } + if (attr->type == mode_attr) { if (mode == MODE_CREATE || mode == MODE_KEYGEN) { - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { + if (attr->ulValueLen == 0 || attr->pValue == NULL) { TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); return CKR_ATTRIBUTE_VALUE_INVALID; } - switch (*((CK_ULONG *)attr->pValue)) { - case IBM_DILITHIUM_KEYFORM_ROUND2: - return CKR_OK; - default: - TRACE_ERROR("%s\n", ock_err(CKR_ATTRIBUTE_VALUE_INVALID)); + oid = find_pqc_by_oid(oids, attr->pValue, attr->ulValueLen); + if (oid == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); return CKR_ATTRIBUTE_VALUE_INVALID; } + return CKR_OK; } TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); return CKR_ATTRIBUTE_READ_ONLY; + } + + return CKR_OK; +} + +// ibm_dilithium_publ_validate_attribute() +// +CK_RV ibm_dilithium_publ_validate_attribute(STDLL_TokData_t *tokdata, + TEMPLATE *tmpl, CK_ATTRIBUTE *attr, + CK_ULONG mode) +{ + CK_RV rc; + + switch (attr->type) { + case CKA_IBM_DILITHIUM_KEYFORM: + case CKA_IBM_DILITHIUM_MODE: + rc = ibm_pqc_validate_keyform_mode(attr, mode, CKM_IBM_DILITHIUM); + if (rc != CKR_OK) + return rc; + return CKR_OK; + case CKA_IBM_DILITHIUM_RHO: + case CKA_IBM_DILITHIUM_T1: + case CKA_VALUE: + if (mode == MODE_CREATE) + return CKR_OK; + TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); + return CKR_ATTRIBUTE_READ_ONLY; default: return publ_key_validate_attribute(tokdata, tmpl, attr, mode); } @@ -5361,7 +5622,15 @@ TEMPLATE *tmpl, CK_ATTRIBUTE *attr, CK_ULONG mode) { + CK_RV rc; + switch (attr->type) { + case CKA_IBM_DILITHIUM_KEYFORM: + case CKA_IBM_DILITHIUM_MODE: + rc = ibm_pqc_validate_keyform_mode(attr, mode, CKM_IBM_DILITHIUM); + if (rc != CKR_OK) + return rc; + return CKR_OK; case CKA_IBM_DILITHIUM_RHO: case CKA_IBM_DILITHIUM_SEED: case CKA_IBM_DILITHIUM_TR: @@ -5369,24 +5638,62 @@ case CKA_IBM_DILITHIUM_S2: case CKA_IBM_DILITHIUM_T0: case CKA_IBM_DILITHIUM_T1: + case CKA_VALUE: if (mode == MODE_CREATE) return CKR_OK; TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); return CKR_ATTRIBUTE_READ_ONLY; - case CKA_IBM_DILITHIUM_KEYFORM: - if (mode == MODE_CREATE || mode == MODE_KEYGEN) { - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - switch (*((CK_ULONG *)attr->pValue)) { - case IBM_DILITHIUM_KEYFORM_ROUND2: - return CKR_OK; - default: - TRACE_ERROR("%s\n", ock_err(CKR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - } + default: + return priv_key_validate_attribute(tokdata, tmpl, attr, mode); + } +} + +// ibm_kyber_publ_validate_attribute() +// +CK_RV ibm_kyber_publ_validate_attribute(STDLL_TokData_t *tokdata, + TEMPLATE *tmpl, CK_ATTRIBUTE *attr, + CK_ULONG mode) +{ + CK_RV rc; + + switch (attr->type) { + case CKA_IBM_KYBER_KEYFORM: + case CKA_IBM_KYBER_MODE: + rc = ibm_pqc_validate_keyform_mode(attr, mode, CKM_IBM_KYBER); + if (rc != CKR_OK) + return rc; + return CKR_OK; + case CKA_IBM_KYBER_PK: + case CKA_VALUE: + if (mode == MODE_CREATE) + return CKR_OK; + TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); + return CKR_ATTRIBUTE_READ_ONLY; + default: + return publ_key_validate_attribute(tokdata, tmpl, attr, mode); + } +} + +// ibm_kyber_priv_validate_attribute() +// +CK_RV ibm_kyber_priv_validate_attribute(STDLL_TokData_t *tokdata, + TEMPLATE *tmpl, CK_ATTRIBUTE *attr, + CK_ULONG mode) +{ + CK_RV rc; + + switch (attr->type) { + case CKA_IBM_KYBER_KEYFORM: + case CKA_IBM_KYBER_MODE: + rc = ibm_pqc_validate_keyform_mode(attr, mode, CKM_IBM_KYBER); + if (rc != CKR_OK) + return rc; + return CKR_OK; + case CKA_IBM_KYBER_SK: + case CKA_IBM_KYBER_PK: + case CKA_VALUE: + if (mode == MODE_CREATE) + return CKR_OK; TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); return CKR_ATTRIBUTE_READ_ONLY; default: @@ -5567,7 +5874,7 @@ always_sens_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_BBOOL)); if (!class_attr || !sensitive_attr || !encrypt_attr || !decrypt_attr - || !sign_attr || !verify_attr | !wrap_attr || !unwrap_attr + || !sign_attr || !verify_attr || !wrap_attr || !unwrap_attr || !extractable_attr || !never_extr_attr || !always_sens_attr) { TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); rc = CKR_HOST_MEMORY; @@ -5962,432 +6269,6 @@ return rc; } - -// rc2_check_required_attributes() -// -CK_RV rc2_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_ULONG val; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - rc = template_attribute_get_ulong(tmpl, CKA_VALUE_LEN, &val); - if (rc != CKR_OK) { - if (mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_VALUE_LEN\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// rc2_set_default_attributes() -// -CK_RV rc2_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *value_len_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_ULONG len = 0L; - CK_RV rc; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - value_len_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_ULONG)); - - if (!type_attr || !value_attr || !value_len_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - value_len_attr->type = CKA_VALUE_LEN; - value_len_attr->ulValueLen = sizeof(CK_ULONG); - value_len_attr->pValue = (CK_BYTE *) value_len_attr + sizeof(CK_ATTRIBUTE); - *(CK_ULONG *) value_len_attr->pValue = len; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_RC2; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - rc = template_update_attribute(tmpl, value_len_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_len_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - if (value_len_attr) - free(value_len_attr); - - return rc; -} - - -// rc2_validate_attribute() -// -CK_RV rc2_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - // rc2 key length <= 128 bytes - // - if (attr->ulValueLen > 128) - return CKR_ATTRIBUTE_VALUE_INVALID; - - return CKR_OK; - case CKA_VALUE_LEN: - { - CK_ULONG len; - - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - if (mode != MODE_KEYGEN && mode != MODE_DERIVE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - len = *(CK_ULONG *) attr->pValue; - if (len > 128) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - } - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// rc4_set_default_attributes() -// -CK_RV rc4_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *value_len_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_ULONG len = 0L; - CK_RV rc; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - value_len_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_ULONG)); - - if (!type_attr || !value_attr || !value_len_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - value_len_attr->type = CKA_VALUE_LEN; - value_len_attr->ulValueLen = sizeof(CK_ULONG); - value_len_attr->pValue = (CK_BYTE *) value_len_attr + sizeof(CK_ATTRIBUTE); - *(CK_ULONG *) value_len_attr->pValue = len; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_RC4; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - rc = template_update_attribute(tmpl, value_len_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_len_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - if (value_len_attr) - free(value_len_attr); - - return rc; -} - - -// rc4_check_required_attributes() -// -CK_RV rc4_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_ULONG val; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - rc = template_attribute_get_ulong(tmpl, CKA_VALUE_LEN, &val); - if (rc != CKR_OK) { - if (mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_VALUE_LEN\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// rc4_validate_attribute() -// -CK_RV rc4_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - // key length <= 256 bytes - // - if (attr->ulValueLen > 256) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - case CKA_VALUE_LEN: - { - CK_ULONG len; - - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - if (mode != MODE_KEYGEN && mode != MODE_DERIVE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - len = *(CK_ULONG *) attr->pValue; - if (len > 255) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - } - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// rc5_check_required_attributes() -// -CK_RV rc5_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_ULONG val; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - rc = template_attribute_get_ulong(tmpl, CKA_VALUE_LEN, &val); - if (rc != CKR_OK) { - if (mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_VALUE_LEN\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// rc5_set_default_attributes() -// -CK_RV rc5_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *value_len_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_ULONG len = 0L; - CK_RV rc; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - value_len_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_ULONG)); - - if (!type_attr || !value_attr || !value_len_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - value_len_attr->type = CKA_VALUE_LEN; - value_len_attr->ulValueLen = sizeof(CK_ULONG); - value_len_attr->pValue = (CK_BYTE *) value_len_attr + sizeof(CK_ATTRIBUTE); - *(CK_ULONG *) value_len_attr->pValue = len; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_RC5; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - rc = template_update_attribute(tmpl, value_len_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_len_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - if (value_len_attr) - free(value_len_attr); - - return rc; -} - - -// rc5_validate_attribute() -// -CK_RV rc5_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - // key length <= 256 bytes - // - if (attr->ulValueLen > 255) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - case CKA_VALUE_LEN: - { - CK_ULONG len; - - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - if (mode != MODE_KEYGEN && mode != MODE_DERIVE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - len = *(CK_ULONG *) attr->pValue; - if (len > 255) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - } - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - // // CK_RV des_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) @@ -7026,969 +6907,10 @@ return CKR_OK; } - -// cast_check_required_attributes() -// -CK_RV cast_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_ULONG val; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - rc = template_attribute_get_ulong(tmpl, CKA_VALUE_LEN, &val); - if (rc != CKR_OK) { - if (mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_VALUE_LEN\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// cast_set_default_attributes() -// -CK_RV cast_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *value_len_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_ULONG len = 0L; - CK_RV rc; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - value_len_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_ULONG)); - - if (!type_attr || !value_attr || !value_len_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - value_len_attr->type = CKA_VALUE_LEN; - value_len_attr->ulValueLen = sizeof(CK_ULONG); - value_len_attr->pValue = (CK_BYTE *) value_len_attr + sizeof(CK_ATTRIBUTE); - *(CK_ULONG *) value_len_attr->pValue = len; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_CAST; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - rc = template_update_attribute(tmpl, value_len_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_len_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - if (value_len_attr) - free(value_len_attr); - - return rc; -} - - -// cast_validate_attribute() -// -CK_RV cast_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - CK_ULONG len; - - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - if (attr->ulValueLen > 8 || attr->ulValueLen < 1) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - case CKA_VALUE_LEN: - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - if (mode != MODE_KEYGEN && mode != MODE_DERIVE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - len = *(CK_ULONG *) attr->pValue; - if (len > 8 || len < 1) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// cast3_check_required_attributes() -// -CK_RV cast3_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_ULONG val; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - rc = template_attribute_get_ulong(tmpl, CKA_VALUE_LEN, &val); - if (rc != CKR_OK) { - if (mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_VALUE_LEN\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// cast3_set_default_attributes() -// -CK_RV cast3_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *value_len_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_ULONG len = 0L; - CK_RV rc; - - if (mode) - value_attr = NULL; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - value_len_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_ULONG)); - - if (!type_attr || !value_attr || !value_len_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - value_len_attr->type = CKA_VALUE_LEN; - value_len_attr->ulValueLen = sizeof(CK_ULONG); - value_len_attr->pValue = (CK_BYTE *) value_len_attr + sizeof(CK_ATTRIBUTE); - *(CK_ULONG *) value_len_attr->pValue = len; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_CAST3; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - rc = template_update_attribute(tmpl, value_len_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_len_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - if (value_len_attr) - free(value_len_attr); - - return rc; -} - - -// cast3_validate_attribute() -// -CK_RV cast3_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - CK_ULONG len; - - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - if (attr->ulValueLen > 8 || attr->ulValueLen < 1) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - case CKA_VALUE_LEN: - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - if (mode != MODE_KEYGEN && mode != MODE_DERIVE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - len = *(CK_ULONG *) attr->pValue; - if (len > 8 || len < 1) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// cast5_check_required_attributes() -// -CK_RV cast5_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_ULONG val; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - rc = template_attribute_get_ulong(tmpl, CKA_VALUE_LEN, &val); - if (rc != CKR_OK) { - if (mode == MODE_KEYGEN) { - TRACE_ERROR("Could not find CKA_VALUE_LEN\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// cast5_set_default_attributes() -// -CK_RV cast5_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *value_len_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_ULONG len = 0L; - CK_RV rc; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - value_len_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_ULONG)); - - if (!type_attr || !value_attr || !value_len_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - value_len_attr->type = CKA_VALUE_LEN; - value_len_attr->ulValueLen = sizeof(CK_ULONG); - value_len_attr->pValue = (CK_BYTE *) value_len_attr + sizeof(CK_ATTRIBUTE); - *(CK_ULONG *) value_len_attr->pValue = len; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_CAST5; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - rc = template_update_attribute(tmpl, value_len_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_len_attr = NULL; - - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - if (value_len_attr) - free(value_len_attr); - - return rc; -} - - -// cast5_validate_attribute() -// -CK_RV cast5_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - CK_ULONG len; - - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - if (attr->ulValueLen > 16 || attr->ulValueLen < 1) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - case CKA_VALUE_LEN: - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - if (mode != MODE_KEYGEN && mode != MODE_DERIVE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - len = *(CK_ULONG *) attr->pValue; - if (len < 1 || len > 16) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// idea_check_required_attributes() -// -CK_RV idea_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// idea_set_default_attributes() -// -CK_RV idea_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_RV rc; - - if (mode) - value_attr = NULL; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - if (!type_attr || !value_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_IDEA; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - - return rc; -} - - -// idea_validate_attribute() -// -CK_RV idea_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - if (attr->ulValueLen != 16) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// cdmf_check_required_attributes() -// -CK_RV cdmf_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -#if !(NOCDMF) -// cdmf_set_default_attributes() -// -CK_RV cdmf_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_RV rc; - - if (mode) - value_attr = NULL; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - - if (!type_attr || !value_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_CDMF; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - - return rc; -} - - -// cdmf_validate_attribute() -// -CK_RV cdmf_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - CK_ULONG len; - - switch (attr->type) { - case CKA_VALUE: -#if 0 - CDMF_Transform_Args args; -#endif - CK_ULONG req_len, repl_len; - CK_BYTE cdmf_key[DES_KEY_SIZE]; - CK_RV rc; - - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - if (attr->ulValueLen != DES_KEY_SIZE || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } -#if 0 - req_len = sizeof(args); - repl_len = DES_KEY_SIZE; - - memcpy(args.des_key, attr->pValue, DES_KEY_SIZE); - - rc = communicate(PK_CDMF_TRANSFORM_KEY, - &args, req_len, cdmf_key, &repl_len, NULL, 0, NULL, 0); - - if (rc != CKR_OK) - return rc; - - if (rc == CKR_OK) { - if (repl_len != DES_KEY_SIZE) - return CKR_GENERAL_ERROR; - - memcpy(attr->pValue, cdmf_key, DES_KEY_SIZE); - } - - return CKR_OK; -#else - return tok_cdmf_transform(attr->pValue, DES_KEY_SIZE); -#endif - case CKA_VALUE_LEN: - if (attr->ulValueLen != sizeof(CK_ULONG) || attr->pValue == NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - if (tokdata->nv_token_data->tweak_vector.netscape_mods == TRUE) { - if (mode == MODE_CREATE || mode == MODE_KEYGEN) { - len = *(CK_ULONG *) attr->pValue; - if (len != DES_KEY_SIZE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - } - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_TYPE_INVALID)); - return CKR_ATTRIBUTE_TYPE_INVALID; - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - -#endif - -// skipjack_check_required_attributes() -// -CK_RV skipjack_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// skipjack_set_default_attributes() -// -CK_RV skipjack_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_RV rc; - - if (mode) - value_attr = NULL; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - - if (!type_attr || !value_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_SKIPJACK; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - - return rc; -} - - -// skipjack_validate_attribute() -// -CK_RV skipjack_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - if (attr->ulValueLen != 20) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// baton_check_required_attributes() -// -CK_RV baton_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// baton_set_default_attributes() -// -CK_RV baton_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_RV rc; - - if (mode) - value_attr = NULL; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - - if (!type_attr || !value_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_BATON; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - - return rc; -} - - -// baton_validate_attribute() -// -CK_RV baton_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - if (attr->ulValueLen != 40) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - -// juniper_check_required_attributes() -// -CK_RV juniper_check_required_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *attr = NULL; - CK_RV rc; - - rc = template_attribute_get_non_empty(tmpl, CKA_VALUE, &attr); - if (rc != CKR_OK) { - if (mode == MODE_CREATE) { - TRACE_ERROR("Could not find CKA_VALUE\n"); - return rc; - } - } - - return secret_key_check_required_attributes(tmpl, mode); -} - - -// juniper_set_default_attributes() -// -CK_RV juniper_set_default_attributes(TEMPLATE *tmpl, CK_ULONG mode) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *type_attr = NULL; - CK_RV rc; - - if (mode) - value_attr = NULL; - - secret_key_set_default_attributes(tmpl, mode); - - type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE)); - - if (!type_attr || !value_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = 0; - value_attr->pValue = NULL; - - type_attr->type = CKA_KEY_TYPE; - type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_JUNIPER; - - rc = template_update_attribute(tmpl, type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - type_attr = NULL; - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - - return CKR_OK; - -error: - if (type_attr) - free(type_attr); - if (value_attr) - free(value_attr); - - return rc; -} - - -// juniper_validate_attribute() -// -CK_RV juniper_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) -{ - switch (attr->type) { - case CKA_VALUE: - if (mode != MODE_CREATE) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_READ_ONLY)); - return CKR_ATTRIBUTE_READ_ONLY; - } - if (attr->ulValueLen != 40) { - TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); - return CKR_ATTRIBUTE_VALUE_INVALID; - } - return CKR_OK; - default: - return secret_key_validate_attribute(tokdata, tmpl, attr, mode); - } -} - - // aes_set_default_attributes() // -CK_RV aes_set_default_attributes(TEMPLATE *tmpl, TEMPLATE *basetmpl, CK_ULONG mode) +CK_RV aes_set_default_attributes(TEMPLATE *tmpl, TEMPLATE *basetmpl, + CK_ULONG mode, CK_BBOOL xts) { CK_ATTRIBUTE *value_attr = NULL; CK_ATTRIBUTE *type_attr = NULL; @@ -8018,7 +6940,7 @@ type_attr->type = CKA_KEY_TYPE; type_attr->ulValueLen = sizeof(CK_KEY_TYPE); type_attr->pValue = (CK_BYTE *) type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) type_attr->pValue = CKK_AES; + *(CK_KEY_TYPE *) type_attr->pValue = xts ? CKK_AES_XTS : CKK_AES; rc = template_update_attribute(tmpl, type_attr); if (rc != CKR_OK) { @@ -8092,7 +7014,7 @@ // // CK_RV aes_validate_attribute(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, - CK_ATTRIBUTE *attr, CK_ULONG mode) + CK_ATTRIBUTE *attr, CK_ULONG mode, CK_BBOOL xts) { CK_ULONG val; @@ -8101,9 +7023,9 @@ // key length is either 16, 24 or 32 bytes // if (mode == MODE_CREATE) { - if (attr->ulValueLen != AES_KEY_SIZE_128 && - attr->ulValueLen != AES_KEY_SIZE_192 && - attr->ulValueLen != AES_KEY_SIZE_256) { + if (attr->ulValueLen != (AES_KEY_SIZE_128 * (xts ? 2 : 1)) && + (xts || attr->ulValueLen != AES_KEY_SIZE_192) && + attr->ulValueLen != (AES_KEY_SIZE_256 * (xts ? 2 : 1))) { TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -8124,8 +7046,9 @@ return CKR_ATTRIBUTE_VALUE_INVALID; } val = *(CK_ULONG *) attr->pValue; - if (val != AES_KEY_SIZE_128 && - val != AES_KEY_SIZE_192 && val != AES_KEY_SIZE_256) { + if (val != (AES_KEY_SIZE_128 * (xts ? 2 : 1)) && + (xts || val != AES_KEY_SIZE_192) && + val != (AES_KEY_SIZE_256 * (xts ? 2 : 1))) { TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -8138,7 +7061,6 @@ } } - // // CK_RV aes_wrap_get_data(TEMPLATE *tmpl, @@ -8182,7 +7104,7 @@ CK_RV aes_unwrap(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, CK_BYTE *data, - CK_ULONG data_len, CK_BBOOL fromend) + CK_ULONG data_len, CK_BBOOL fromend, CK_BBOOL xts) { CK_ATTRIBUTE *value_attr = NULL; CK_ATTRIBUTE *val_len_attr = NULL; @@ -8212,8 +7134,9 @@ key_size = data_len; /* key_size should be one of AES's possible sizes */ - if (key_size != AES_KEY_SIZE_128 && - key_size != AES_KEY_SIZE_192 && key_size != AES_KEY_SIZE_256) { + if (key_size != (AES_KEY_SIZE_128 * (xts ? 2 : 1)) && + (xts || key_size != AES_KEY_SIZE_192) && + key_size != (AES_KEY_SIZE_256 * (xts ? 2 : 1))) { TRACE_ERROR("%s\n", ock_err(ERR_WRAPPED_KEY_LEN_RANGE)); return CKR_WRAPPED_KEY_LEN_RANGE; } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/key_mgr.c opencryptoki-3.20.0+dfsg/usr/lib/common/key_mgr.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/key_mgr.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/key_mgr.c 2023-02-13 09:22:42.000000000 +0100 @@ -35,6 +35,7 @@ #include "attributes.h" #include "tok_spec_struct.h" #include "trace.h" +#include "pqc_defs.h" #include "../api/policy.h" #include "../api/statistics.h" @@ -115,16 +116,6 @@ subclass = CKK_DES3; break; -#if !(NOCDMF) - case CKM_CDMF_KEY_GEN: - if (subclass != 0 && subclass != CKK_CDMF) { - TRACE_ERROR("%s\n", ock_err(ERR_TEMPLATE_INCONSISTENT)); - return CKR_TEMPLATE_INCONSISTENT; - } - - subclass = CKK_CDMF; - break; -#endif case CKM_SSL3_PRE_MASTER_KEY_GEN: if (subclass != 0 && subclass != CKK_GENERIC_SECRET) { TRACE_ERROR("%s\n", ock_err(ERR_TEMPLATE_INCONSISTENT)); @@ -146,6 +137,14 @@ subclass = CKK_AES; break; + case CKM_AES_XTS_KEY_GEN: + if (subclass != 0 && subclass != CKK_AES_XTS) { + TRACE_ERROR("%s\n", ock_err(ERR_TEMPLATE_INCONSISTENT)); + return CKR_TEMPLATE_INCONSISTENT; + } + + subclass = CKK_AES_XTS; + break; case CKM_GENERIC_SECRET_KEY_GEN: if (subclass != 0 && subclass != CKK_GENERIC_SECRET) { TRACE_ERROR("%s\n", ock_err(ERR_TEMPLATE_INCONSISTENT)); @@ -180,19 +179,15 @@ case CKM_DES3_KEY_GEN: rc = ckm_des3_key_gen(tokdata, key_obj->template); break; -#if !(NOCDMF) - case CKM_CDMF_KEY_GEN: - rc = ckm_cdmf_key_gen(tokdata, key_obj->template); - break; -#endif case CKM_SSL3_PRE_MASTER_KEY_GEN: rc = ckm_ssl3_pre_master_key_gen(tokdata, key_obj->template, mech); break; -#ifndef NOAES case CKM_AES_KEY_GEN: - rc = ckm_aes_key_gen(tokdata, key_obj->template); + rc = ckm_aes_key_gen(tokdata, key_obj->template, FALSE); + break; + case CKM_AES_XTS_KEY_GEN: + rc = ckm_aes_key_gen(tokdata, key_obj->template, TRUE); break; -#endif case CKM_GENERIC_SECRET_KEY_GEN: rc = ckm_generic_secret_key_gen(tokdata, key_obj->template); break; @@ -799,10 +794,6 @@ // A secret key can be used to wrap a private key. switch (mech->mechanism) { -#if !(NOCDMF) - case CKM_CDMF_CBC: - case CKM_CDMF_CBC_PAD: -#endif case CKM_DES_CBC: case CKM_DES3_ECB: case CKM_DES3_CBC: @@ -814,6 +805,7 @@ case CKM_AES_CFB8: case CKM_AES_CFB64: case CKM_AES_CFB128: + case CKM_AES_XTS: if ((class != CKO_SECRET_KEY) && (class != CKO_PRIVATE_KEY)) { TRACE_ERROR ("Specified mechanism only wraps secret & private keys.\n"); @@ -821,7 +813,6 @@ goto done; } break; - case CKM_CDMF_ECB: case CKM_DES_ECB: case CKM_AES_ECB: case CKM_AES_CBC: @@ -869,9 +860,6 @@ } switch (keytype) { -#if !(NOCDMF) - case CKK_CDMF: -#endif case CKK_DES: rc = des_wrap_get_data(key_obj->template, length_only, &data, &data_len); @@ -924,8 +912,8 @@ goto done; } break; -#ifndef NOAES case CKK_AES: + case CKK_AES_XTS: rc = aes_wrap_get_data(key_obj->template, length_only, &data, &data_len); if (rc != CKR_OK) { @@ -933,7 +921,6 @@ goto done; } break; -#endif case CKK_EC: rc = ecdsa_priv_wrap_get_data(key_obj->template, length_only, &data, &data_len); @@ -952,10 +939,6 @@ // we might need to format the wrapped data based on the mechanism // switch (mech->mechanism) { -#if !(NOCMF) - case CKM_CDMF_ECB: - case CKM_CDMF_CBC: -#endif case CKM_DES_ECB: case CKM_DES_CBC: case CKM_DES3_ECB: @@ -970,7 +953,6 @@ goto done; } break; -#ifndef NOAES case CKM_AES_ECB: case CKM_AES_CBC: case CKM_AES_CTR: @@ -988,20 +970,16 @@ goto done; } break; -#endif -#if !(NOCMF) - case CKM_CDMF_CBC_PAD: -#endif case CKM_DES_CBC_PAD: case CKM_DES3_CBC_PAD: case CKM_AES_CBC_PAD: // these mechanisms pad themselves // break; - case CKM_RSA_PKCS_OAEP: case CKM_RSA_PKCS: case CKM_RSA_X_509: + case CKM_AES_XTS: break; default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_INVALID)); @@ -1160,7 +1138,6 @@ } switch (mech->mechanism) { - case CKM_CDMF_ECB: case CKM_DES_ECB: case CKM_AES_ECB: case CKM_AES_CBC: @@ -1173,10 +1150,6 @@ goto done; } break; -#if !(NOCMF) - case CKM_CDMF_CBC: - case CKM_CDMF_CBC_PAD: -#endif case CKM_DES_CBC: case CKM_DES3_ECB: case CKM_DES3_CBC: @@ -1188,6 +1161,7 @@ case CKM_DES_CBC_PAD: case CKM_DES3_CBC_PAD: case CKM_AES_CBC_PAD: + case CKM_AES_XTS: if ((keyclass != CKO_SECRET_KEY) && (keyclass != CKO_PRIVATE_KEY)) { TRACE_ERROR("Specified mech unwraps secret & private keys only.\n"); rc = CKR_ARGUMENTS_BAD; @@ -1218,13 +1192,9 @@ */ switch (mech->mechanism) { case CKM_RSA_X_509: - case CKM_CDMF_ECB: case CKM_DES_ECB: case CKM_AES_ECB: case CKM_AES_CBC: -#if !(NOCMF) - case CKM_CDMF_CBC: -#endif case CKM_DES_CBC: case CKM_DES3_ECB: case CKM_DES3_CBC: @@ -1233,7 +1203,9 @@ case CKM_AES_CFB8: case CKM_AES_CFB64: case CKM_AES_CFB128: - if (keytype != CKK_AES && keytype != CKK_GENERIC_SECRET) { + case CKM_AES_XTS: + if (keytype != CKK_AES && keytype != CKK_AES_XTS && + keytype != CKK_GENERIC_SECRET) { TRACE_ERROR("The key type does not allow CKA_VALUE_LEN to be " "specified in the unwrapping template.\n"); rc = CKR_TEMPLATE_INCONSISTENT; @@ -1413,7 +1385,7 @@ { CK_BYTE *alg = NULL; CK_BYTE *priv_key = NULL; - CK_ULONG alg_len; + CK_ULONG alg_len, i; CK_RV rc; rc = ber_decode_PrivateKeyInfo(keydata, keylen, &alg, &alg_len, &priv_key); @@ -1453,14 +1425,28 @@ return CKR_OK; } } - // Check only the OBJECT IDENTIFIER for DILITHIUM + // Check only the OBJECT IDENTIFIERs for DILITHIUM // - if (alg_len >= ber_idDilithiumLen) { - if (memcmp(alg, ber_idDilithium, ber_idDilithiumLen) == 0) { + for (i = 0; dilithium_oids[i].oid != NULL; i++) { + if (alg_len == dilithium_oids[i].oid_len + ber_NULLLen && + memcmp(alg, dilithium_oids[i].oid, + dilithium_oids[i].oid_len) == 0 && + memcmp(alg + dilithium_oids[i].oid_len, + ber_NULL, ber_NULLLen) == 0) { *keytype = CKK_IBM_PQC_DILITHIUM; return CKR_OK; } } + // Check only the OBJECT IDENTIFIERs for KYBER + // + for (i = 0; kyber_oids[i].oid != NULL; i++) { + if (alg_len == kyber_oids[i].oid_len + ber_NULLLen && + memcmp(alg, kyber_oids[i].oid, kyber_oids[i].oid_len) == 0 && + memcmp(alg + kyber_oids[i].oid_len, ber_NULL, ber_NULLLen) == 0) { + *keytype = CKK_IBM_PQC_KYBER; + return CKR_OK; + } + } TRACE_ERROR("%s\n", ock_err(ERR_TEMPLATE_INCOMPLETE)); return CKR_TEMPLATE_INCOMPLETE; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/loadsave.c opencryptoki-3.20.0+dfsg/usr/lib/common/loadsave.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/loadsave.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/loadsave.c 2023-02-13 09:22:42.000000000 +0100 @@ -673,7 +673,9 @@ // SHA of (object data) | // ---- end encrypted part <--+ // - compute_sha1(tokdata, obj_data, obj_data_len, hash_sha); + rc = compute_sha1(tokdata, obj_data, obj_data_len, hash_sha); + if (rc != CKR_OK) + goto error; // encrypt the sensitive object data. need to be careful. // if I use the normal high-level encryption routines I'll need to @@ -809,8 +811,14 @@ fclose(fp2); continue; } - //size--; - size = size - sizeof(CK_ULONG_32) - sizeof(CK_BBOOL); + if (size <= sizeof(CK_ULONG_32) + sizeof(CK_BBOOL)) { + fclose(fp2); + OCK_SYSLOG(LOG_ERR, "Improper size of object %s (ignoring it)\n", + fname); + continue; + } + + size -= sizeof(CK_ULONG_32) + sizeof(CK_BBOOL); buf = (CK_BYTE *) malloc(size); if (!buf) { fclose(fp2); @@ -1346,7 +1354,7 @@ CK_BYTE *obj_data = NULL; CK_BYTE *ptr = NULL; CK_BYTE *key = NULL; - CK_ULONG key_len; + CK_ULONG key_len = 0; CK_ULONG block_size; CK_BYTE hash_sha[SHA1_HASH_SIZE]; CK_ULONG clear_len, obj_data_len; @@ -1486,7 +1494,14 @@ goto done; } - size = size - sizeof(CK_ULONG_32) - sizeof(CK_BBOOL); // SAB + if (size <= sizeof(CK_ULONG_32) + sizeof(CK_BBOOL)) { + rc = CKR_FUNCTION_FAILED; + OCK_SYSLOG(LOG_ERR, "Improper size of object %s (ignoring it)\n", + fname); + goto done; + } + + size -= sizeof(CK_ULONG_32) + sizeof(CK_BBOOL); buf = (CK_BYTE *) malloc(size); if (!buf) { @@ -1613,8 +1628,15 @@ fclose(fp2); continue; } - // size--; - size = size - sizeof(CK_ULONG_32) - sizeof(CK_BBOOL); + + if (size <= sizeof(CK_ULONG_32) + sizeof(CK_BBOOL)) { + fclose(fp2); + OCK_SYSLOG(LOG_ERR, "Improper size of object %s (ignoring it)\n", + fname); + continue; + } + + size -= sizeof(CK_ULONG_32) + sizeof(CK_BBOOL); buf = (CK_BYTE *) malloc(size); if (!buf) { fclose(fp2); @@ -2269,6 +2291,21 @@ #define HEADER_LEN 64 #define FOOTER_LEN 16 +/** + * public tok obj layout + * + * ---------------- <--+ + * u32 tokversion | 16-byte header + * u8 private_flag | + * u8 reserved[7] | + * u32 object_len | + * ---------------- <--+ + * u8 object[object_len] | body + * ---------------- <--+ + */ +#define PUB_HEADER_LEN 16 +#define HEADER_COMMON_LEN 5 + // // Note: The token lock (XProcLock) must be held when calling this function. // @@ -2322,6 +2359,8 @@ /* New token objects files created by mkstemp have a size of zero */ if (sb.st_size == 0) { new = 1; + fclose(fp); + fp = NULL; goto do_work; } @@ -2610,7 +2649,7 @@ set_perm(fileno(fp)); - if (fread(header, HEADER_LEN, 1, fp) != 1) { + if (fread(header, HEADER_COMMON_LEN, 1, fp) != 1) { OCK_SYSLOG(LOG_ERR, "Cannot read header\n"); rc = CKR_FUNCTION_FAILED; goto done; @@ -2618,7 +2657,25 @@ memcpy(&ver, header, 4); memcpy(&priv, header + 4, 1); - memcpy(&len, header + 60, 4); + if (priv) { + if (fread(header + HEADER_COMMON_LEN, + HEADER_LEN - HEADER_COMMON_LEN, 1, fp) != 1) { + OCK_SYSLOG(LOG_ERR, "Cannot read header\n"); + rc = CKR_FUNCTION_FAILED; + goto done; + } + + memcpy(&len, header + 60, 4); + } else { + if (fread(header + HEADER_COMMON_LEN, + PUB_HEADER_LEN - HEADER_COMMON_LEN, 1, fp) != 1) { + OCK_SYSLOG(LOG_ERR, "Cannot read header\n"); + rc = CKR_FUNCTION_FAILED; + goto done; + } + + memcpy(&len, header + 12, 4); + } /* * In OCK 3.12 - 3.14 the version and size was not stored in BE. So if @@ -2644,11 +2701,13 @@ rc = CKR_FUNCTION_FAILED; goto done; } - if (fread(footer, FOOTER_LEN, 1, fp) != 1) { - OCK_SYSLOG(LOG_ERR, - "Token object %s appears corrupted (ignoring it)", fname); - rc = CKR_FUNCTION_FAILED; - goto done; + if (priv) { + if (fread(footer, FOOTER_LEN, 1, fp) != 1) { + OCK_SYSLOG(LOG_ERR, + "Token object %s appears corrupted (ignoring it)", fname); + rc = CKR_FUNCTION_FAILED; + goto done; + } } size_64 = size; @@ -2667,20 +2726,6 @@ return rc; } -/** - * public tok obj layout - * - * ---------------- <--+ - * u32 tokversion | 16-byte header - * u8 private_flag | - * u8 reserved[7] | - * u32 object_len | - * ---------------- <--+ - * u8 object[object_len] | body - * ---------------- <--+ - */ -#define PUB_HEADER_LEN 16 - // // Note: The token lock (XProcLock) must be held when calling this function. // diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/lock_sess_mgr.c opencryptoki-3.20.0+dfsg/usr/lib/common/lock_sess_mgr.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/lock_sess_mgr.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/lock_sess_mgr.c 2023-02-13 09:22:42.000000000 +0100 @@ -586,12 +586,14 @@ // // -CK_RV session_mgr_get_op_state(SESSION *sess, +CK_RV session_mgr_get_op_state(STDLL_TokData_t *tokdata, SESSION *sess, CK_BBOOL length_only, CK_BYTE *data, CK_ULONG *data_len) { OP_STATE_DATA *op_data = NULL; - CK_ULONG op_data_len = 0; + CK_ULONG max_data_len = *data_len; + CK_ULONG op_data_len; + CK_ULONG all_data_len = 0; CK_ULONG offset, active_ops; if (!sess) { @@ -614,22 +616,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(ENCR_DECR_CONTEXT) + sess->encr_ctx.context_len + sess->encr_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_ENCR; @@ -653,6 +662,9 @@ sess->encr_ctx.mech.pParameter, sess->encr_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } @@ -662,22 +674,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(ENCR_DECR_CONTEXT) + sess->decr_ctx.context_len + sess->decr_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_DECR; @@ -701,6 +720,9 @@ sess->decr_ctx.mech.pParameter, sess->decr_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } @@ -710,22 +732,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(DIGEST_CONTEXT) + sess->digest_ctx.context_len + sess->digest_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_DIGEST; @@ -749,6 +778,9 @@ sess->digest_ctx.mech.pParameter, sess->digest_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } @@ -758,22 +790,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(SIGN_VERIFY_CONTEXT) + sess->sign_ctx.context_len + sess->sign_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_SIGN; @@ -797,6 +836,9 @@ sess->sign_ctx.mech.pParameter, sess->sign_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } @@ -806,22 +848,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(SIGN_VERIFY_CONTEXT) + sess->verify_ctx.context_len + sess->verify_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_VERIFY; @@ -845,15 +894,18 @@ sess->verify_ctx.mech.pParameter, sess->verify_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } - if (!active_ops) { + if (active_ops == 0) { TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); return CKR_OPERATION_NOT_INITIALIZED; } - *data_len = op_data_len; + *data_len = all_data_len; return CKR_OK; } @@ -865,6 +917,8 @@ CK_OBJECT_HANDLE auth_key, CK_BYTE *data, CK_ULONG data_len) { + CK_BYTE *cur_data; + CK_ULONG cur_data_len; OP_STATE_DATA *op_data = NULL; CK_BYTE *mech_param = NULL; CK_BYTE *context = NULL; @@ -872,226 +926,369 @@ CK_BYTE *ptr2 = NULL; CK_BYTE *ptr3 = NULL; CK_ULONG len; + CK_ULONG encr_key_needed = 0; + CK_ULONG auth_key_needed = 0; if (!sess || !data) { TRACE_ERROR("%s received bad argument(s)\n", __func__); return CKR_FUNCTION_FAILED; } - op_data = (OP_STATE_DATA *) data; - if (data_len < op_data->data_len + sizeof(OP_STATE_DATA)) { + /* + * Validate the new state information. Don't touch the session + * until the new state is valid. + */ + cur_data = data; + cur_data_len = data_len; + while (cur_data_len >= sizeof(OP_STATE_DATA)) { + op_data = (OP_STATE_DATA *)cur_data; + + if (cur_data_len < op_data->data_len + sizeof(OP_STATE_DATA)) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + /* + * Make sure the session states are compatible: same OCK version, + * same token model, same session state. + */ +#ifdef PACKAGE_VERSION + if (strncmp((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)) != 0) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } +#endif + if (memcmp(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)) != 0 || + memcmp(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)) != 0) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + if (sess->session_info.state != op_data->session_state) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + switch (op_data->active_operation) { + case STATE_ENCR: + case STATE_DECR: + { + ENCR_DECR_CONTEXT *ctx = + (ENCR_DECR_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(ENCR_DECR_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + encr_key_needed++; + } + break; + + case STATE_SIGN: + case STATE_VERIFY: + { + SIGN_VERIFY_CONTEXT *ctx = + (SIGN_VERIFY_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(SIGN_VERIFY_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + auth_key_needed++; + } + break; + + case STATE_DIGEST: + { + DIGEST_CONTEXT *ctx = + (DIGEST_CONTEXT *) (cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(DIGEST_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + } + break; + default: + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + /* move on to next operation */ + cur_data_len -= (op_data->data_len + sizeof(OP_STATE_DATA)); + cur_data += (op_data->data_len + sizeof(OP_STATE_DATA)); + } + /* nothing must be left over */ + if (cur_data_len > 0) { TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); return CKR_SAVED_STATE_INVALID; } - // make sure the session states are compatible - // - if (sess->session_info.state != op_data->session_state) { - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; + if (encr_key_needed > 0 && encr_key == CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); + return CKR_KEY_NEEDED; } - // validate the new state information. don't touch the session - // until the new state is valid. - // - switch (op_data->active_operation) { - case STATE_ENCR: - case STATE_DECR: - { - ENCR_DECR_CONTEXT *ctx = - (ENCR_DECR_CONTEXT *) (data + sizeof(OP_STATE_DATA)); - - len = - sizeof(ENCR_DECR_CONTEXT) + ctx->context_len + - ctx->mech.ulParameterLen; - if (len != op_data->data_len) { - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; - } - if (auth_key != CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); - return CKR_KEY_NOT_NEEDED; - } - if (encr_key == CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); - return CKR_KEY_NEEDED; - } - ptr1 = (CK_BYTE *) ctx; - ptr2 = ptr1 + sizeof(ENCR_DECR_CONTEXT); - ptr3 = ptr2 + ctx->context_len; - - if (ctx->context_len) { - context = (CK_BYTE *) malloc(ctx->context_len); - if (!context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(context, ptr2, ctx->context_len); - } - - if (ctx->mech.ulParameterLen) { - mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); - if (!mech_param) { - if (context) - free(context); - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); - } - } - break; - case STATE_SIGN: - case STATE_VERIFY: - { - SIGN_VERIFY_CONTEXT *ctx = - (SIGN_VERIFY_CONTEXT *) (data + sizeof(OP_STATE_DATA)); - - len = - sizeof(SIGN_VERIFY_CONTEXT) + ctx->context_len + - ctx->mech.ulParameterLen; - if (len != op_data->data_len) { - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; - } - if (auth_key == CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); - return CKR_KEY_NEEDED; - } - if (encr_key != CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); - return CKR_KEY_NOT_NEEDED; - } - ptr1 = (CK_BYTE *) ctx; - ptr2 = ptr1 + sizeof(SIGN_VERIFY_CONTEXT); - ptr3 = ptr2 + ctx->context_len; - - if (ctx->context_len) { - context = (CK_BYTE *) malloc(ctx->context_len); - if (!context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(context, ptr2, ctx->context_len); - } - - if (ctx->mech.ulParameterLen) { - mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); - if (!mech_param) { - if (context) - free(context); - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); - } - } - break; - case STATE_DIGEST: - { - DIGEST_CONTEXT *ctx = - (DIGEST_CONTEXT *) (data + sizeof(OP_STATE_DATA)); - - len = - sizeof(DIGEST_CONTEXT) + ctx->context_len + - ctx->mech.ulParameterLen; - if (len != op_data->data_len) { - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; - } - if (auth_key != CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); - return CKR_KEY_NOT_NEEDED; - } - if (encr_key != CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); - return CKR_KEY_NOT_NEEDED; - } - ptr1 = (CK_BYTE *) ctx; - ptr2 = ptr1 + sizeof(DIGEST_CONTEXT); - ptr3 = ptr2 + ctx->context_len; - - if (ctx->context_len) { - context = (CK_BYTE *) malloc(ctx->context_len); - if (!context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(context, ptr2, ctx->context_len); - } - - if (ctx->mech.ulParameterLen) { - mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); - if (!mech_param) { - if (context) - free(context); - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; + if (encr_key_needed == 0 && encr_key != CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); + return CKR_KEY_NOT_NEEDED; + } + if (auth_key_needed > 0 && auth_key == CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); + return CKR_KEY_NEEDED; + } + if (auth_key_needed == 0 && auth_key != CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); + return CKR_KEY_NOT_NEEDED; + } + + /* State information looks okay. Cleanup the current session state, first */ + if (sess->encr_ctx.active) + encr_mgr_cleanup(tokdata, sess, &sess->encr_ctx); + if (sess->decr_ctx.active) + decr_mgr_cleanup(tokdata, sess, &sess->decr_ctx); + if (sess->digest_ctx.active) + digest_mgr_cleanup(tokdata, sess, &sess->digest_ctx); + if (sess->sign_ctx.active) + sign_mgr_cleanup(tokdata, sess, &sess->sign_ctx); + if (sess->verify_ctx.active) + verify_mgr_cleanup(tokdata, sess, &sess->verify_ctx); + + /* Now process the saved operation states */ + cur_data = data; + cur_data_len = data_len; + while (cur_data_len >= sizeof(OP_STATE_DATA)) { + op_data = (OP_STATE_DATA *)cur_data; + + if (cur_data_len < op_data->data_len + sizeof(OP_STATE_DATA)) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + switch (op_data->active_operation) { + case STATE_ENCR: + case STATE_DECR: + { + ENCR_DECR_CONTEXT *ctx = + (ENCR_DECR_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(ENCR_DECR_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + if (encr_key == CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); + return CKR_KEY_NEEDED; + } + ptr1 = (CK_BYTE *) ctx; + ptr2 = ptr1 + sizeof(ENCR_DECR_CONTEXT); + ptr3 = ptr2 + ctx->context_len; + + if (ctx->context_len) { + context = (CK_BYTE *) malloc(ctx->context_len); + if (!context) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(context, ptr2, ctx->context_len); + } + + if (ctx->mech.ulParameterLen) { + mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); + if (!mech_param) { + if (context) + free(context); + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); + } + } + break; + + case STATE_SIGN: + case STATE_VERIFY: + { + SIGN_VERIFY_CONTEXT *ctx = + (SIGN_VERIFY_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(SIGN_VERIFY_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + if (auth_key == CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); + return CKR_KEY_NEEDED; + } + ptr1 = (CK_BYTE *) ctx; + ptr2 = ptr1 + sizeof(SIGN_VERIFY_CONTEXT); + ptr3 = ptr2 + ctx->context_len; + + if (ctx->context_len) { + context = (CK_BYTE *) malloc(ctx->context_len); + if (!context) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(context, ptr2, ctx->context_len); + } + + if (ctx->mech.ulParameterLen) { + mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); + if (!mech_param) { + if (context) + free(context); + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); + } + } + break; + + case STATE_DIGEST: + { + DIGEST_CONTEXT *ctx = + (DIGEST_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(DIGEST_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + ptr1 = (CK_BYTE *) ctx; + ptr2 = ptr1 + sizeof(DIGEST_CONTEXT); + ptr3 = ptr2 + ctx->context_len; + + if (ctx->context_len) { + context = (CK_BYTE *) malloc(ctx->context_len); + if (!context) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(context, ptr2, ctx->context_len); + } + + if (ctx->mech.ulParameterLen) { + mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); + if (!mech_param) { + if (context) + free(context); + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); } - memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); } + break; + default: + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; } - break; - default: - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; + + /* copy the new state information */ + switch (op_data->active_operation) { + case STATE_ENCR: + memcpy(&sess->encr_ctx, ptr1, sizeof(ENCR_DECR_CONTEXT)); + + sess->encr_ctx.key = encr_key; + sess->encr_ctx.context = context; + sess->encr_ctx.mech.pParameter = mech_param; + break; + + case STATE_DECR: + memcpy(&sess->decr_ctx, ptr1, sizeof(ENCR_DECR_CONTEXT)); + + sess->decr_ctx.key = encr_key; + sess->decr_ctx.context = context; + sess->decr_ctx.mech.pParameter = mech_param; + break; + + case STATE_SIGN: + memcpy(&sess->sign_ctx, ptr1, sizeof(SIGN_VERIFY_CONTEXT)); + + sess->sign_ctx.key = auth_key; + sess->sign_ctx.context = context; + sess->sign_ctx.mech.pParameter = mech_param; + break; + + case STATE_VERIFY: + memcpy(&sess->verify_ctx, ptr1, sizeof(SIGN_VERIFY_CONTEXT)); + + sess->verify_ctx.key = auth_key; + sess->verify_ctx.context = context; + sess->verify_ctx.mech.pParameter = mech_param; + break; + + case STATE_DIGEST: + memcpy(&sess->digest_ctx, ptr1, sizeof(DIGEST_CONTEXT)); + + sess->digest_ctx.context = context; + sess->digest_ctx.mech.pParameter = mech_param; + break; + } + + context = NULL; + mech_param = NULL; + + /* move on to next operation */ + cur_data_len -= (op_data->data_len + sizeof(OP_STATE_DATA)); + cur_data += (op_data->data_len + sizeof(OP_STATE_DATA)); } + return CKR_OK; +} - // state information looks okay. cleanup the current session state, first - // - if (sess->encr_ctx.active) +CK_RV session_mgr_cancel(STDLL_TokData_t *tokdata, SESSION *sess, + CK_FLAGS flags) +{ + if ((flags & CKF_ENCRYPT) && sess->encr_ctx.active) encr_mgr_cleanup(tokdata, sess, &sess->encr_ctx); - if (sess->decr_ctx.active) + if ((flags & CKF_DECRYPT) && sess->decr_ctx.active) decr_mgr_cleanup(tokdata, sess, &sess->decr_ctx); - if (sess->digest_ctx.active) + if ((flags & CKF_DIGEST) && sess->digest_ctx.active) digest_mgr_cleanup(tokdata, sess, &sess->digest_ctx); - if (sess->sign_ctx.active) + if ((flags & CKF_SIGN) && sess->sign_ctx.active && + !sess->sign_ctx.recover) sign_mgr_cleanup(tokdata, sess, &sess->sign_ctx); - if (sess->verify_ctx.active) + if ((flags & CKF_SIGN_RECOVER) && sess->sign_ctx.active && + sess->sign_ctx.recover) + sign_mgr_cleanup(tokdata, sess, &sess->sign_ctx); + + if ((flags & CKF_VERIFY) && sess->verify_ctx.active && + !sess->verify_ctx.recover) verify_mgr_cleanup(tokdata, sess, &sess->verify_ctx); + if ((flags & CKF_VERIFY_RECOVER) && sess->verify_ctx.active && + sess->verify_ctx.recover) + verify_mgr_cleanup(tokdata, sess, &sess->verify_ctx); - // copy the new state information - // - switch (op_data->active_operation) { - case STATE_ENCR: - memcpy(&sess->encr_ctx, ptr1, sizeof(ENCR_DECR_CONTEXT)); - - sess->encr_ctx.key = encr_key; - sess->encr_ctx.context = context; - sess->encr_ctx.mech.pParameter = mech_param; - break; - case STATE_DECR: - memcpy(&sess->decr_ctx, ptr1, sizeof(ENCR_DECR_CONTEXT)); - - sess->decr_ctx.key = encr_key; - sess->decr_ctx.context = context; - sess->decr_ctx.mech.pParameter = mech_param; - break; - case STATE_SIGN: - memcpy(&sess->sign_ctx, ptr1, sizeof(SIGN_VERIFY_CONTEXT)); - - sess->sign_ctx.key = auth_key; - sess->sign_ctx.context = context; - sess->sign_ctx.mech.pParameter = mech_param; - break; - case STATE_VERIFY: - memcpy(&sess->verify_ctx, ptr1, sizeof(SIGN_VERIFY_CONTEXT)); - - sess->verify_ctx.key = auth_key; - sess->verify_ctx.context = context; - sess->verify_ctx.mech.pParameter = mech_param; - break; - case STATE_DIGEST: - memcpy(&sess->digest_ctx, ptr1, sizeof(DIGEST_CONTEXT)); - - sess->digest_ctx.context = context; - sess->digest_ctx.mech.pParameter = mech_param; - break; + if ((flags & CKF_FIND_OBJECTS) && sess->find_active) { + if (sess->find_list) + free(sess->find_list); + sess->find_list = NULL; + sess->find_len = 0; + sess->find_idx = 0; + sess->find_active = FALSE; } return CKR_OK; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_aes.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_aes.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_aes.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_aes.c 2023-02-13 09:22:42.000000000 +0100 @@ -488,6 +488,85 @@ return rc; } +static CK_RV aes_xts_crypt(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + CK_BBOOL encrypt, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + AES_XTS_CONTEXT *context; + OBJECT *key = NULL; + CK_RV rc; + + if (!sess || !ctx || !out_data_len) { + TRACE_ERROR("%s received bad argument(s)\n", __func__); + return CKR_FUNCTION_FAILED; + } + context = (AES_XTS_CONTEXT *)ctx->context; + + /* CKM_AES_XTS requires the input data to be at least one full block */ + if (in_data_len < AES_BLOCK_SIZE) { + TRACE_ERROR("%s\n", ock_err(ERR_DATA_LEN_RANGE)); + return CKR_DATA_LEN_RANGE; + } + + rc = object_mgr_find_in_map1(tokdata, ctx->key, &key, READ_LOCK); + if (rc != CKR_OK) { + TRACE_ERROR("Failed to find specified object.\n"); + return rc; + } + + if (length_only == TRUE) { + *out_data_len = in_data_len; + rc = CKR_OK; + goto done; + } + + if (*out_data_len < in_data_len) { + *out_data_len = in_data_len; + TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); + rc = CKR_BUFFER_TOO_SMALL; + goto done; + } + + rc = ckm_aes_xts_crypt(tokdata, in_data, in_data_len, out_data, + out_data_len, ctx->mech.pParameter, key, + TRUE, TRUE, context->iv, encrypt); + +done: + object_put(tokdata, key, TRUE); + key = NULL; + + return rc; +} + +CK_RV aes_xts_encrypt(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + return aes_xts_crypt(tokdata, sess, length_only, TRUE, ctx, + in_data, in_data_len, out_data, out_data_len); +} + +CK_RV aes_xts_decrypt(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + return aes_xts_crypt(tokdata, sess, length_only, FALSE, ctx, + in_data, in_data_len, out_data, out_data_len); +} + // // CK_RV aes_ecb_encrypt_update(STDLL_TokData_t *tokdata, @@ -1191,6 +1270,135 @@ } } +static CK_RV aes_xts_crypt_update(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + CK_BBOOL encrypt, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + AES_XTS_CONTEXT *context = NULL; + OBJECT *key = NULL; + CK_BYTE *clear = NULL; + CK_ULONG total, remain, out_len; + CK_RV rc; + + if (!sess || !ctx || !out_data_len) { + TRACE_ERROR("%s received bad argument(s)\n", __func__); + return CKR_FUNCTION_FAILED; + } + context = (AES_XTS_CONTEXT *)ctx->context; + + total = (context->len + in_data_len); + + if (total < 2 * AES_BLOCK_SIZE) { + if (length_only == FALSE && in_data_len > 0) { + memcpy(context->data + context->len, in_data, in_data_len); + context->len += in_data_len; + } + + *out_data_len = 0; + return CKR_OK; + } + + /* We have at least 2 full blocks, keep at least one full block */ + remain = AES_BLOCK_SIZE + (total % AES_BLOCK_SIZE); + out_len = total - remain; + + if (length_only == TRUE) { + *out_data_len = out_len; + return CKR_OK; + } + + if (*out_data_len < out_len) + return CKR_BUFFER_TOO_SMALL; + + rc = object_mgr_find_in_map_nocache(tokdata, ctx->key, &key, READ_LOCK); + if (rc != CKR_OK) { + TRACE_ERROR("Failed to find specified object.\n"); + return rc; + } + + if (out_len < context->len) { + rc = ckm_aes_xts_crypt(tokdata, context->data, out_len, out_data, + out_data_len, ctx->mech.pParameter, key, + !context->initialized, FALSE, context->iv, + encrypt); + if (rc == CKR_OK) { + TRACE_ERROR("ckm_aes_xts_crypt failed\n"); + goto out; + } + + memmove(context->data, context->data + out_len, + context->len - out_len); + context->len -= out_len; + + memcpy(context->data + context->len, in_data, in_data_len); + context->len += in_data_len; + + context->initialized = TRUE; + } else { + clear = (CK_BYTE *) malloc(out_len); + if (!clear) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + goto out; + } + + memcpy(clear, context->data, context->len); + memcpy(clear + context->len, in_data, out_len - context->len); + + rc = ckm_aes_xts_crypt(tokdata, clear, out_len, out_data, + out_data_len, ctx->mech.pParameter, key, + !context->initialized, FALSE, context->iv, + encrypt); + if (rc == CKR_OK) { + if (remain != 0) + memcpy(context->data, in_data + (in_data_len - remain), + remain); + context->len = remain; + + context->initialized = TRUE; + } else { + TRACE_ERROR("ckm_aes_xts_crypt failed\n"); + } + + free(clear); + } + +out: + object_put(tokdata, key, TRUE); + key = NULL; + + return rc; +} + +CK_RV aes_xts_encrypt_update(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + return aes_xts_crypt_update(tokdata, sess, length_only, TRUE, ctx, + in_data, in_data_len, out_data, out_data_len); +} + +CK_RV aes_xts_decrypt_update(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + return aes_xts_crypt_update(tokdata, sess, length_only, FALSE, ctx, + in_data, in_data_len, out_data, out_data_len); +} + // // CK_RV aes_ecb_encrypt_final(STDLL_TokData_t *tokdata, @@ -1556,6 +1764,73 @@ return CKR_OK; } +static CK_RV aes_xts_crypt_final(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + CK_BBOOL encrypt, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + AES_XTS_CONTEXT *context = NULL; + OBJECT *key = NULL; + CK_RV rc; + + + if (!sess || !ctx || !out_data_len) { + TRACE_ERROR("%s received bad argument(s)\n", __func__); + return CKR_FUNCTION_FAILED; + } + context = (AES_XTS_CONTEXT *)ctx->context; + + if (length_only) { + *out_data_len = context->len; + return CKR_OK; + } + + rc = object_mgr_find_in_map_nocache(tokdata, ctx->key, &key, READ_LOCK); + if (rc != CKR_OK) { + TRACE_ERROR("Failed to find specified object.\n"); + return rc; + } + + rc = ckm_aes_xts_crypt(tokdata, context->data, context->len, out_data, + out_data_len, ctx->mech.pParameter, key, + !context->initialized, TRUE, context->iv, + encrypt); + if (rc == CKR_OK) { + *out_data_len = context->len; + + memset(context, 0, sizeof(*context)); + } else { + TRACE_ERROR("ckm_aes_xts_crypt failed\n"); + } + + object_put(tokdata, key, TRUE); + key = NULL; + + return CKR_OK; +} + +CK_RV aes_xts_encrypt_final(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + return aes_xts_crypt_final(tokdata, sess, length_only, TRUE, ctx, + out_data, out_data_len); +} + +CK_RV aes_xts_decrypt_final(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_BBOOL length_only, + ENCR_DECR_CONTEXT *ctx, + CK_BYTE *out_data, CK_ULONG *out_data_len) +{ + return aes_xts_crypt_final(tokdata, sess, length_only, FALSE, ctx, + out_data, out_data_len); +} + CK_RV aes_ofb_encrypt(STDLL_TokData_t *tokdata, SESSION *sess, CK_BBOOL length_only, @@ -3427,6 +3702,7 @@ to->pIv = NULL; to->ulIvLen = 0; + to->ulIvBits = 0; if (from->ulIvLen != 0 && from->pIv != NULL) { to->pIv = malloc(from->ulIvLen); if (to->pIv == NULL) { @@ -3437,6 +3713,7 @@ memcpy(to->pIv, from->pIv, from->ulIvLen); to->ulIvLen = from->ulIvLen; + to->ulIvBits = from->ulIvBits; } to->pAAD = NULL; @@ -3472,6 +3749,17 @@ return CKR_OK; } +void aes_gcm_param_from_compat(const CK_GCM_PARAMS_COMPAT *from, + CK_GCM_PARAMS *to) +{ + to->pIv = from->pIv; + to->ulIvLen = from->ulIvLen; + to->ulIvBits = from->ulIvLen * 8; + to->pAAD = from->pAAD; + to->ulAADLen = from->ulAADLen; + to->ulTagBits = from->ulTagBits; +} + // // mechanisms // @@ -3479,7 +3767,7 @@ // // -CK_RV ckm_aes_key_gen(STDLL_TokData_t *tokdata, TEMPLATE *tmpl) +CK_RV ckm_aes_key_gen(STDLL_TokData_t *tokdata, TEMPLATE *tmpl, CK_BBOOL xts) { CK_ATTRIBUTE *opaque_attr = NULL; CK_ATTRIBUTE *value_attr = NULL; @@ -3498,8 +3786,10 @@ return rc; } - if (key_size != AES_KEY_SIZE_128 && - key_size != AES_KEY_SIZE_192 && key_size != AES_KEY_SIZE_256) { + if (key_size != (AES_KEY_SIZE_128 * (xts ? 2 : 1)) && + (xts || key_size != AES_KEY_SIZE_192) && + key_size != (AES_KEY_SIZE_256 * (xts ? 2 : 1))) { + TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); return CKR_ATTRIBUTE_VALUE_INVALID; } @@ -3508,9 +3798,12 @@ return CKR_MECHANISM_INVALID; } - rc = token_specific.t_aes_key_gen(tokdata, &aes_key, &token_keysize, - key_size, &is_opaque); - + if (xts) + rc = token_specific.t_aes_xts_key_gen(tokdata, &aes_key, &token_keysize, + key_size, &is_opaque); + else + rc = token_specific.t_aes_key_gen(tokdata, &aes_key, &token_keysize, + key_size, &is_opaque); if (rc != CKR_OK) goto err; @@ -3568,7 +3861,7 @@ key_type_attr->type = CKA_KEY_TYPE; key_type_attr->ulValueLen = sizeof(CK_KEY_TYPE); key_type_attr->pValue = (CK_BYTE *) key_type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) key_type_attr->pValue = CKK_AES; + *(CK_KEY_TYPE *) key_type_attr->pValue = xts ? CKK_AES_XTS : CKK_AES; class_attr->type = CKA_CLASS; class_attr->ulValueLen = sizeof(CK_OBJECT_CLASS); @@ -3883,5 +4176,165 @@ } } + return CKR_OK; +} + +CK_RV ckm_aes_xts_crypt(STDLL_TokData_t *tokdata, + CK_BYTE *in_data, + CK_ULONG in_data_len, + CK_BYTE *out_data, + CK_ULONG *out_data_len, + CK_BYTE *tweak, OBJECT *key, + CK_BBOOL initial, CK_BBOOL final, + CK_BYTE *iv, CK_BBOOL encrypt) +{ + CK_ULONG rc; + + if (!in_data || !out_data || !tweak || !iv || !key) { + TRACE_ERROR("%s received bad argument(s)\n", __func__); + return CKR_FUNCTION_FAILED; + } + if (*out_data_len < in_data_len) { + *out_data_len = in_data_len; + TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); + return CKR_BUFFER_TOO_SMALL; + } + + if (token_specific.t_aes_xts == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_INVALID)); + return CKR_MECHANISM_INVALID; + } + + rc = token_specific.t_aes_xts(tokdata, in_data, in_data_len, + out_data, out_data_len, key, tweak, encrypt, + initial, final, iv); + + if (rc != CKR_OK) + TRACE_DEVEL("Token specific aes xts encrypt failed.\n"); + + return rc; +} + +CK_RV aes_xts_cipher(CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len, + CK_BYTE *tweak, CK_BOOL encrypt, CK_BBOOL initial, + CK_BBOOL final, CK_BYTE* iv, + CK_RV (*iv_from_tweak)(CK_BYTE *tweak, CK_BYTE* iv, + void * cb_data), + CK_RV (*cipher_blocks)(CK_BYTE *in, CK_BYTE *out, + CK_ULONG len, CK_BYTE *iv, + void * cb_data), + void *cb_data) +{ + unsigned char partial[AES_BLOCK_SIZE]; + unsigned char iv_prev[AES_INIT_VECTOR_SIZE] = { 0 }; + CK_ULONG len, rest; + CK_RV rc; + + /* Full block size unless final call */ + if (!final && (in_data_len % AES_BLOCK_SIZE) != 0) + return CKR_DATA_LEN_RANGE; + /* Final block must be at least one full block */ + if (final && in_data_len < AES_BLOCK_SIZE) + return CKR_DATA_LEN_RANGE; + + if (out_data == NULL) { + *out_data_len = in_data_len; + return CKR_OK; + } + + if (*out_data_len < in_data_len) + return CKR_BUFFER_TOO_SMALL; + + /* Calculate IV from tweak if initial call, otherwise IV is already set */ + if (initial) { + rc = iv_from_tweak(tweak, iv, cb_data); + if (rc != CKR_OK) { + TRACE_ERROR("iv_from_tweak callback failed\n"); + return rc; + } + } + + rest = in_data_len % AES_BLOCK_SIZE; + len = in_data_len - rest; + *out_data_len = 0; + + /* + * It was checked above that we have at least one full block if we are in + * the final call. + */ + if (!encrypt && final) + len -= AES_BLOCK_SIZE; + + /* process full blocks */ + if (len > 0) { + rc = cipher_blocks(in_data, out_data, len, iv, cb_data); + if (rc != CKR_OK) { + TRACE_ERROR("cipher_blocks callback failed\n"); + return rc; + } + + in_data += len; + in_data_len -= len; + out_data += len; + *out_data_len = len; + } + + if (!encrypt && final) { + /* Remember IV of block n-1 */ + memcpy(iv_prev, iv, AES_BLOCK_SIZE); + + rc = cipher_blocks(in_data, out_data, AES_BLOCK_SIZE, iv, cb_data); + if (rc != CKR_OK) { + TRACE_ERROR("cipher_blocks callback failed\n"); + return rc; + } + + in_data += AES_BLOCK_SIZE; + in_data_len -= AES_BLOCK_SIZE; + out_data += AES_BLOCK_SIZE; + *out_data_len += AES_BLOCK_SIZE; + } + + /* Partial block? Only possible for final call */ + if (final && in_data_len > 0) { + /* + * It was checked above that we had at least one previous + * block if we are in the final call, thus + * 'out_data - AES_BLOCK_SIZE' or 'in_data - AES_BLOCK_SIZE' is OK. + */ + if (!encrypt) { + /* + * For decrypt: The last complete block uses the + * IV from n-1, and the very last incomplete block + * uses the IV from n. + */ + rc = cipher_blocks(in_data - AES_BLOCK_SIZE, + out_data - AES_BLOCK_SIZE, + AES_BLOCK_SIZE, iv, cb_data); + if (rc != CKR_OK) { + TRACE_ERROR("cipher_blocks callback failed\n"); + return rc; + } + + /* Restore IV from block n-1 */ + memcpy(iv, iv_prev, AES_BLOCK_SIZE); + } + + /* Steal ciphertext to complete the block */ + memcpy(partial, in_data, in_data_len); + memcpy(out_data, out_data - AES_BLOCK_SIZE, in_data_len); + memcpy(partial + in_data_len, out_data - AES_BLOCK_SIZE + in_data_len, + AES_BLOCK_SIZE - in_data_len); + *out_data_len += in_data_len; + + rc = cipher_blocks(partial, out_data - AES_BLOCK_SIZE, + AES_BLOCK_SIZE, iv, cb_data); + if (rc != CKR_OK) { + TRACE_ERROR("cipher_blocks callback failed\n"); + return rc; + } + } + return CKR_OK; } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_des.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_des.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_des.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_des.c 2023-02-13 09:22:42.000000000 +0100 @@ -1347,106 +1347,6 @@ return rc; } -#if !(NOCDMF) - -// -// -CK_RV ckm_cdmf_key_gen(STDLL_TokData_t *tokdata, TEMPLATE *tmpl) -{ - CK_ATTRIBUTE *value_attr = NULL; - CK_ATTRIBUTE *key_type_attr = NULL; - CK_ATTRIBUTE *class_attr = NULL; - CK_ATTRIBUTE *local_attr = NULL; - CK_BYTE cdmf_key[DES_KEY_SIZE]; - CK_ULONG repl_len, expected_repl_len; - CK_ULONG rc; - - repl_len = expected_repl_len = DES_KEY_SIZE; - - rc = communicate(PK_CDMF_KEYGEN, - NULL, 0, cdmf_key, &repl_len, NULL, 0, NULL, 0); - - if (rc == CKR_OK) { - if (repl_len != expected_repl_len) - return CKR_GENERAL_ERROR; - } - - value_attr = (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + DES_KEY_SIZE); - key_type_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_KEY_TYPE)); - class_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_OBJECT_CLASS)); - local_attr = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) + sizeof(CK_BBOOL)); - - if (!value_attr || !key_type_attr || !class_attr || !local_attr) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - goto error; - } - - value_attr->type = CKA_VALUE; - value_attr->ulValueLen = DES_KEY_SIZE; - value_attr->pValue = (CK_BYTE *) value_attr + sizeof(CK_ATTRIBUTE); - memcpy(value_attr->pValue, cdmf_key, DES_KEY_SIZE); - - key_type_attr->type = CKA_KEY_TYPE; - key_type_attr->ulValueLen = sizeof(CK_KEY_TYPE); - key_type_attr->pValue = (CK_BYTE *) key_type_attr + sizeof(CK_ATTRIBUTE); - *(CK_KEY_TYPE *) key_type_attr->pValue = CKK_CDMF; - - class_attr->type = CKA_CLASS; - class_attr->ulValueLen = sizeof(CK_OBJECT_CLASS); - class_attr->pValue = (CK_BYTE *) class_attr + sizeof(CK_ATTRIBUTE); - *(CK_OBJECT_CLASS *) class_attr->pValue = CKO_SECRET_KEY; - - local_attr->type = CKA_LOCAL; - local_attr->ulValueLen = sizeof(CK_BBOOL); - local_attr->pValue = (CK_BYTE *) local_attr + sizeof(CK_ATTRIBUTE); - *(CK_BBOOL *) local_attr->pValue = TRUE; - - rc = template_update_attribute(tmpl, value_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - value_attr = NULL; - rc = template_update_attribute(tmpl, key_type_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - key_type_attr = NULL; - rc = template_update_attribute(tmpl, class_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - class_attr = NULL; - rc = template_update_attribute(tmpl, local_attr); - if (rc != CKR_OK) { - TRACE_ERROR("template_update_attribute failed\n"); - goto error; - } - local_attr = NULL; - - return CKR_OK; - -error: - if (value_attr) - free(value_attr); - if (key_type_attr) - free(key_type_attr); - if (class_attr) - free(class_attr); - if (local_attr) - free(local_attr); - - return rc; -} - -#endif - // // CK_RV ckm_des_ecb_encrypt(STDLL_TokData_t *tokdata, diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_ec.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_ec.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_ec.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_ec.c 2023-02-13 09:22:42.000000000 +0100 @@ -891,12 +891,12 @@ case CKM_DES3_KEY_GEN: *type = CKK_DES3; break; - case CKM_CDMF_KEY_GEN: - *type = CKK_CDMF; - break; case CKM_AES_KEY_GEN: *type = CKK_AES; break; + case CKM_AES_XTS_KEY_GEN: + *type = CKK_AES_XTS; + break; case CKM_GENERIC_SECRET_KEY_GEN: *type = CKK_GENERIC_SECRET; break; @@ -915,6 +915,9 @@ case CKM_IBM_DILITHIUM: *type = CKK_IBM_PQC_DILITHIUM; break; + case CKM_IBM_KYBER: + *type = CKK_IBM_PQC_KYBER; + break; default: return CKR_MECHANISM_INVALID; } @@ -1015,6 +1018,14 @@ return CKR_TEMPLATE_INCONSISTENT; } break; + case CKK_AES_XTS: + if (*key_len != (AES_KEY_SIZE_128 * 2) && + *key_len != (AES_KEY_SIZE_256 * 2)) { + TRACE_ERROR("Derived key length does not work for the key " + "type\n"); + return CKR_TEMPLATE_INCONSISTENT; + } + break; default: /* DES/DES2/DE3 has already been checked above */ break; @@ -1148,6 +1159,7 @@ switch (keytype) { case CKK_GENERIC_SECRET: case CKK_AES: + case CKK_AES_XTS: /* Supply CKA_VAUE_LEN since this is required for those key types */ rc = build_attribute(CKA_VALUE_LEN, (CK_BYTE*)&key_len, sizeof(key_len), &vallen_attr); @@ -1393,7 +1405,7 @@ group = EC_GROUP_new_by_curve_name(nid); if (group == NULL) { - rc = CKR_FUNCTION_FAILED; + rc = CKR_CURVE_NOT_SUPPORTED; goto done; } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_md2.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_md2.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_md2.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_md2.c 2023-02-13 09:22:42.000000000 +0100 @@ -22,6 +22,8 @@ #include +#if !(NOMD2) + // Permutation of 0..255 constructed from the digits of pi. It gives a // "random" nonlinear byte substitution operation. // @@ -507,3 +509,5 @@ t = checksum[i] ^= S[block[i] ^ t]; } + +#endif diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_md5.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_md5.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_md5.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_md5.c 2023-02-13 09:22:42.000000000 +0100 @@ -242,15 +242,7 @@ CK_ULONG in_data_len, CK_BYTE *out_data, CK_ULONG *out_data_len) { - OBJECT *key_obj = NULL; - CK_ATTRIBUTE *attr = NULL; - CK_BYTE hash[MD5_HASH_SIZE]; - DIGEST_CONTEXT digest_ctx; - CK_MECHANISM digest_mech; - CK_BYTE k_ipad[MD5_BLOCK_SIZE]; - CK_BYTE k_opad[MD5_BLOCK_SIZE]; - CK_ULONG key_bytes, hash_len, hmac_len; - CK_ULONG i; + CK_ULONG hmac_len; CK_RV rc; if (!sess || !ctx || !out_data_len) { @@ -274,142 +266,16 @@ return CKR_OK; } - memset(&digest_ctx, 0x0, sizeof(DIGEST_CONTEXT)); + rc = openssl_specific_hmac_init(tokdata, ctx, &ctx->mech, ctx->key); + if (rc != CKR_OK) + return rc; + + rc = openssl_specific_hmac(ctx, in_data, in_data_len, + out_data, out_data_len, TRUE); + if (rc != CKR_OK) + return rc; - rc = object_mgr_find_in_map1(tokdata, ctx->key, &key_obj, READ_LOCK); - if (rc != CKR_OK) { - TRACE_ERROR("Failed to acquire key from specified handle.\n"); - if (rc == CKR_OBJECT_HANDLE_INVALID) - return CKR_KEY_HANDLE_INVALID; - else - return rc; - } - - rc = template_attribute_get_non_empty(key_obj->template, CKA_VALUE, &attr); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_VALUE in the template\n"); - goto done; - } - - key_bytes = attr->ulValueLen; - - - // build (K XOR ipad), (K XOR opad) - // - if (key_bytes > MD5_BLOCK_SIZE) { - digest_mech.mechanism = CKM_MD5; - digest_mech.ulParameterLen = 0; - digest_mech.pParameter = NULL; - - rc = digest_mgr_init(tokdata, sess, &digest_ctx, &digest_mech, FALSE); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Init failed.\n"); - goto done; - } - - hash_len = sizeof(hash); - rc = digest_mgr_digest(tokdata, sess, FALSE, &digest_ctx, - attr->pValue, attr->ulValueLen, hash, &hash_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Digest failed.\n"); - digest_mgr_cleanup(tokdata, sess, &digest_ctx); - goto done; - } - - memset(&digest_ctx, 0x0, sizeof(DIGEST_CONTEXT)); - - for (i = 0; i < hash_len; i++) { - k_ipad[i] = hash[i] ^ 0x36; - k_opad[i] = hash[i] ^ 0x5C; - } - - memset(&k_ipad[i], 0x36, MD5_BLOCK_SIZE - i); - memset(&k_opad[i], 0x5C, MD5_BLOCK_SIZE - i); - } else { - CK_BYTE *key = attr->pValue; - - for (i = 0; i < key_bytes; i++) { - k_ipad[i] = key[i] ^ 0x36; - k_opad[i] = key[i] ^ 0x5C; - } - - memset(&k_ipad[i], 0x36, MD5_BLOCK_SIZE - key_bytes); - memset(&k_opad[i], 0x5C, MD5_BLOCK_SIZE - key_bytes); - } - - digest_mech.mechanism = CKM_MD5; - digest_mech.ulParameterLen = 0; - digest_mech.pParameter = NULL; - - // inner hash - // - rc = digest_mgr_init(tokdata, sess, &digest_ctx, &digest_mech, FALSE); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Init failed.\n"); - goto done; - } - - rc = digest_mgr_digest_update(tokdata, sess, &digest_ctx, k_ipad, - MD5_BLOCK_SIZE); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Update failed.\n"); - goto done; - } - - rc = digest_mgr_digest_update(tokdata, sess, &digest_ctx, in_data, - in_data_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Update failed.\n"); - goto done; - } - - hash_len = sizeof(hash); - rc = digest_mgr_digest_final(tokdata, sess, FALSE, &digest_ctx, hash, - &hash_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Final failed.\n"); - goto done; - } - - memset(&digest_ctx, 0x0, sizeof(DIGEST_CONTEXT)); - - // outer hash - // - rc = digest_mgr_init(tokdata, sess, &digest_ctx, &digest_mech, FALSE); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Init failed.\n"); - goto done; - } - - rc = digest_mgr_digest_update(tokdata, sess, &digest_ctx, k_opad, - MD5_BLOCK_SIZE); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Update failed.\n"); - goto done; - } - - rc = digest_mgr_digest_update(tokdata, sess, &digest_ctx, hash, hash_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Update failed.\n"); - goto done; - } - - hash_len = sizeof(hash); - rc = digest_mgr_digest_final(tokdata, sess, FALSE, &digest_ctx, hash, - &hash_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Final failed.\n"); - goto done; - } - - memcpy(out_data, hash, hmac_len); - *out_data_len = hmac_len; - -done: - object_put(tokdata, key_obj, TRUE); - key_obj = NULL; - - return rc; + return CKR_OK; } CK_RV md5_hmac_verify(STDLL_TokData_t *tokdata, SESSION *sess, @@ -417,48 +283,21 @@ CK_BYTE *in_data, CK_ULONG in_data_len, CK_BYTE *signature, CK_ULONG sig_len) { - CK_BYTE hmac[MD5_HASH_SIZE]; - SIGN_VERIFY_CONTEXT hmac_ctx; - CK_ULONG hmac_len, len; CK_RV rc; - if (!sess || !ctx || !in_data || !signature) { + if (!sess || !ctx || !signature) { TRACE_ERROR("%s received bad argument(s)\n", __func__); return CKR_FUNCTION_FAILED; } - if (ctx->mech.mechanism == CKM_MD5_HMAC_GENERAL) - hmac_len = *(CK_ULONG *) ctx->mech.pParameter; - else - hmac_len = MD5_HASH_SIZE; - - memset(&hmac_ctx, 0, sizeof(SIGN_VERIFY_CONTEXT)); - - rc = sign_mgr_init(tokdata, sess, &hmac_ctx, &ctx->mech, FALSE, ctx->key, - FALSE); - if (rc != CKR_OK) { - TRACE_DEVEL("Sign Mgr Init failed.\n"); - goto done; - } - len = sizeof(hmac); - rc = sign_mgr_sign(tokdata, sess, FALSE, &hmac_ctx, in_data, in_data_len, - hmac, &len); - if (rc != CKR_OK) { - TRACE_DEVEL("Sign Mgr Sign failed.\n"); - goto done; - } - if ((len != hmac_len) || (len != sig_len)) { - TRACE_ERROR("%s\n", ock_err(ERR_SIGNATURE_LEN_RANGE)); - rc = CKR_SIGNATURE_LEN_RANGE; - goto done; - } - - if (CRYPTO_memcmp(hmac, signature, hmac_len) != 0) { - TRACE_ERROR("%s\n", ock_err(ERR_SIGNATURE_INVALID)); - rc = CKR_SIGNATURE_INVALID; - } + rc = openssl_specific_hmac_init(tokdata, ctx, &ctx->mech, ctx->key); + if (rc != CKR_OK) + return rc; + + rc = openssl_specific_hmac(ctx, in_data, in_data_len, + signature, &sig_len, FALSE); + if (rc != CKR_OK) + return rc; -done: - sign_mgr_cleanup(tokdata, sess, &hmac_ctx); - return rc; + return CKR_OK; } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_openssl.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_openssl.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_openssl.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_openssl.c 2023-02-13 09:22:42.000000000 +0100 @@ -50,6 +50,7 @@ const BIGNUM *bignum = NULL; #else BIGNUM *bignum = NULL; + int try; #endif CK_BYTE *ssl_ptr = NULL; BIGNUM *e = NULL; @@ -117,11 +118,29 @@ #if !OPENSSL_VERSION_PREREQ(3, 0) e = NULL; // will be freed as part of the context #endif +#if OPENSSL_VERSION_PREREQ(3, 0) + /* + * In OpenSSL 3.0 the RSA key gen algorithm has been changed and can now + * fail to generate a key. Retry up to 10 times in such a case. + */ + for (try = 1; try <= 10; try++) { + if (EVP_PKEY_keygen(ctx, &pkey) == 1) { + rc = CKR_OK; + break; + } + + TRACE_ERROR("%s (try %d)\n", ock_err(ERR_FUNCTION_FAILED), try); + rc = CKR_FUNCTION_FAILED; + } + if (rc != CKR_OK) + goto done; +#else if (EVP_PKEY_keygen(ctx, &pkey) != 1) { TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); rc = CKR_FUNCTION_FAILED; goto done; } +#endif #if !OPENSSL_VERSION_PREREQ(3, 0) if ((rsa = EVP_PKEY_get0_RSA(pkey)) == NULL) { TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); @@ -1873,15 +1892,17 @@ CK_BYTE *ecpoint = NULL; CK_ULONG ecpoint_len, privlen; CK_BBOOL allocated = FALSE; + int len; CK_RV rc; - privlen = ec_prime_len_from_nid(nid); - if (privlen <= 0) { + len = ec_prime_len_from_nid(nid); + if (len <= 0) { TRACE_ERROR("ec_prime_len_from_nid failed\n"); rc = CKR_CURVE_NOT_SUPPORTED; goto out; } + privlen = len; rc = ec_point_from_public_data(data, data_len, privlen, allow_raw, &allocated, &ecpoint, &ecpoint_len); @@ -2211,6 +2232,7 @@ BN_CTX *bnctx = NULL; #else BIGNUM *bn_d = NULL; + int len; #endif CK_BYTE *ecpoint = NULL, *enc_ecpoint = NULL, *d = NULL; CK_ULONG ecpoint_len, enc_ecpoint_len, d_len; @@ -2340,7 +2362,13 @@ goto out; } - d_len = ec_prime_len_from_nid(nid); + len = ec_prime_len_from_nid(nid); + if (len <= 0) { + TRACE_ERROR("ec_prime_len_from_nid failed\n"); + rc = CKR_CURVE_NOT_SUPPORTED; + goto out; + } + d_len = len; d = OPENSSL_zalloc(d_len); if (d == NULL) { TRACE_ERROR("OPENSSL_zalloc failed\n"); @@ -2417,6 +2445,7 @@ size_t siglen; CK_BYTE *sigbuf = NULL; const unsigned char *p; + int len; UNUSED(tokdata); UNUSED(sess); @@ -2469,12 +2498,13 @@ ECDSA_SIG_get0(sig, &r, &s); - privlen = ec_prime_len_from_pkey(ec_key); - if (privlen <= 0) { + len = ec_prime_len_from_pkey(ec_key); + if (len <= 0) { TRACE_ERROR("ec_prime_len_from_pkey failed\n"); rc = CKR_FUNCTION_FAILED; goto out; } + privlen = len; /* Insert leading 0's if r or s shorter than privlen */ n = privlen - BN_num_bytes(r); @@ -2512,6 +2542,7 @@ ECDSA_SIG *sig = NULL; BIGNUM *r = NULL, *s = NULL; CK_RV rc = CKR_OK; + int len; size_t siglen; CK_BYTE *sigbuf = NULL; EVP_PKEY_CTX *ctx = NULL; @@ -2523,12 +2554,13 @@ if (rc != CKR_OK) return rc; - privlen = ec_prime_len_from_pkey(ec_key); - if (privlen <= 0) { + len = ec_prime_len_from_pkey(ec_key); + if (len <= 0) { TRACE_ERROR("ec_prime_len_from_pkey failed\n"); rc = CKR_FUNCTION_FAILED; goto out; } + privlen = len; if (signature_len < 2 * privlen) { TRACE_ERROR("Signature is too short\n"); @@ -2556,12 +2588,13 @@ goto out; } - siglen = i2d_ECDSA_SIG(sig, &sigbuf); - if (siglen <= 0) { + len = i2d_ECDSA_SIG(sig, &sigbuf); + if (len <= 0) { TRACE_ERROR("i2d_ECDSA_SIG failed\n"); rc = CKR_FUNCTION_FAILED; goto out; } + siglen = len; ctx = EVP_PKEY_CTX_new(ec_key, NULL); if (ctx == NULL) { @@ -2619,7 +2652,7 @@ EVP_PKEY *ec_pub = NULL, *ec_priv = NULL; EVP_PKEY_CTX *ctx = NULL; size_t secret_len; - int nid; + int nid, len; CK_RV rc; UNUSED(tokdata); @@ -2721,7 +2754,13 @@ goto out; } - secret_len = ec_prime_len_from_nid(nid); + len = ec_prime_len_from_nid(nid); + if (len <= 0) { + TRACE_ERROR("ec_prime_len_from_nid failed\n"); + rc = CKR_CURVE_NOT_SUPPORTED; + goto out; + } + secret_len = len; if (EVP_PKEY_derive(ctx, secret_value, &secret_len) <= 0) { TRACE_DEVEL("ECDH_compute_key failed\n"); rc = CKR_FUNCTION_FAILED; @@ -3135,7 +3174,6 @@ if (keytype == CKK_DES3 && keylen == DES_KEY_SIZE * 3) return EVP_des_ede3_cfb64(); break; -#ifndef NOAES case CKM_AES_ECB: if (keytype != CKK_AES) break; @@ -3234,7 +3272,18 @@ break; } break; -#endif + case CKM_AES_XTS: + if (keytype != CKK_AES_XTS) + break; + switch (keylen * 8) { + case 256: + return EVP_aes_128_xts(); + case 512: + return EVP_aes_256_xts(); + default: + break; + } + break; default: TRACE_ERROR("mechanism 0x%lx not supported\n", mech); return NULL; @@ -3281,7 +3330,9 @@ #else blocksize = EVP_CIPHER_get_block_size(cipher); #endif - if (in_data_len % blocksize || in_data_len > INT_MAX) { + if ((mech == CKM_AES_XTS ? in_data_len < AES_BLOCK_SIZE : + in_data_len % blocksize) || + in_data_len > INT_MAX) { TRACE_ERROR("%s\n", ock_err(ERR_DATA_LEN_RANGE)); return CKR_DATA_LEN_RANGE; } @@ -3520,9 +3571,6 @@ return rv; } - -#ifndef NOAES - CK_RV openssl_specific_aes_ecb(STDLL_TokData_t *tokdata, CK_BYTE *in_data, CK_ULONG in_data_len, @@ -4062,7 +4110,169 @@ first, last, ctx); } -#endif +static EVP_CIPHER_CTX *aes_xts_init_ecb_cipher_ctx(const CK_BYTE *key, + CK_ULONG keylen, + CK_BBOOL encrypt) +{ + const EVP_CIPHER *cipher; + EVP_CIPHER_CTX *ctx = NULL; + + if (key == NULL) + return NULL; + + switch (keylen) { + case AES_KEY_SIZE_128: + cipher = EVP_aes_128_ecb(); + break; + case AES_KEY_SIZE_256: + cipher = EVP_aes_256_ecb(); + break; + default: + TRACE_ERROR("Key size wrong: %lu.\n", keylen); + return NULL; + } + + ctx = EVP_CIPHER_CTX_new(); + if (ctx == NULL) { + TRACE_ERROR("EVP_CIPHER_CTX_new failed\n"); + return NULL; + } + + if (EVP_CipherInit_ex(ctx, cipher, NULL, key, NULL, + encrypt ? 1 : 0) != 1) { + EVP_CIPHER_CTX_free(ctx); + TRACE_ERROR("EVP_CipherInit_ex failed\n"); + return NULL; + } + + return ctx; +} + +static void aes_xts_xor_block(const CK_BYTE *in1, const CK_BYTE *in2, + CK_BYTE *out) +{ + CK_ULONG i; + + for (i = 0; i < AES_BLOCK_SIZE; i++) + out[i] = in1[i] ^ in2[i]; +} + +static void aes_xts_mult(CK_BYTE *iv) +{ + CK_ULONG c, i; + + for (c = 0, i = 0; i < AES_BLOCK_SIZE; ++i) { + c += ((CK_ULONG)iv[i]) << 1; + iv[i] = (CK_BYTE)c; + c = c >> 8; + } + + iv[0] ^= (CK_BYTE)(0x87 & (0 - c)); +} + +struct aes_xts_cb_data { + EVP_CIPHER_CTX *tweak_ctx; + EVP_CIPHER_CTX *cipher_ctx; +}; + +static CK_RV aes_xts_iv_from_tweak(CK_BYTE *tweak, CK_BYTE* iv, void * cb_data) +{ + struct aes_xts_cb_data *data = cb_data; + + if (EVP_Cipher(data->tweak_ctx, iv, tweak, AES_BLOCK_SIZE) <= 0) { + TRACE_ERROR("EVP_Cipher failed\n"); + return CKR_FUNCTION_FAILED; + } + + return CKR_OK; +} + +static CK_RV aes_xts_cipher_blocks(CK_BYTE *in, CK_BYTE *out, CK_ULONG len, + CK_BYTE *iv, void * cb_data) +{ + struct aes_xts_cb_data *data = cb_data; + CK_BYTE buf[AES_INIT_VECTOR_SIZE]; + + while (len >= AES_BLOCK_SIZE) { + aes_xts_xor_block(in, iv, buf); + + if (EVP_Cipher(data->cipher_ctx, out, buf, AES_BLOCK_SIZE) <= 0) { + TRACE_ERROR("EVP_Cipher failed\n"); + return CKR_FUNCTION_FAILED; + } + + aes_xts_xor_block(out, iv, out); + + in += AES_BLOCK_SIZE; + out += AES_BLOCK_SIZE; + len -= AES_BLOCK_SIZE; + + aes_xts_mult(iv); + } + + return CKR_OK; +} + +CK_RV openssl_specific_aes_xts(STDLL_TokData_t *tokdata, + CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len, + OBJECT *key_obj, CK_BYTE *tweak, + CK_BOOL encrypt, CK_BBOOL initial, + CK_BBOOL final, CK_BYTE* iv) +{ + struct aes_xts_cb_data data = { 0 }; + CK_ATTRIBUTE *key_attr; + CK_RV rc; + + UNUSED(tokdata); + + if (initial && final) + return openssl_cipher_perform(key_obj, CKM_AES_XTS, + in_data, in_data_len, + out_data, out_data_len, + tweak, NULL, encrypt); + + rc = template_attribute_get_non_empty(key_obj->template, CKA_VALUE, + &key_attr); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find CKA_VALUE for the key.\n"); + return rc; + } + + if (initial) { + data.tweak_ctx = aes_xts_init_ecb_cipher_ctx( + (CK_BYTE *)key_attr->pValue + key_attr->ulValueLen / 2, + key_attr->ulValueLen / 2, TRUE); + if (data.tweak_ctx == NULL) { + TRACE_ERROR("aes_xts_init_ecb_cipher_ctx failed\n"); + rc = CKR_FUNCTION_FAILED; + goto out; + } + } + + data.cipher_ctx = aes_xts_init_ecb_cipher_ctx((CK_BYTE *)key_attr->pValue, + key_attr->ulValueLen / 2, + encrypt); + if (data.cipher_ctx == NULL) { + TRACE_ERROR("aes_xts_init_ecb_cipher_ctx failed\n"); + rc = CKR_FUNCTION_FAILED; + goto out; + } + + rc = aes_xts_cipher(in_data, in_data_len, out_data, out_data_len, + tweak, encrypt, initial, final, iv, + aes_xts_iv_from_tweak, + aes_xts_cipher_blocks, + &data); + +out: + if (data.tweak_ctx != NULL) + EVP_CIPHER_CTX_free(data.tweak_ctx); + if (data.cipher_ctx != NULL) + EVP_CIPHER_CTX_free(data.cipher_ctx); + + return rc; +} CK_RV openssl_specific_des_ecb(STDLL_TokData_t *tokdata, CK_BYTE *in_data, @@ -4200,6 +4410,16 @@ first, last, ctx); } +static void openssl_specific_hmac_free(STDLL_TokData_t *tokdata, SESSION *sess, + CK_BYTE *context, CK_ULONG context_len) +{ + UNUSED(tokdata); + UNUSED(sess); + UNUSED(context_len); + + EVP_MD_CTX_destroy((EVP_MD_CTX *)context); +} + CK_RV openssl_specific_hmac_init(STDLL_TokData_t *tokdata, SIGN_VERIFY_CONTEXT *ctx, CK_MECHANISM_PTR mech, @@ -4239,6 +4459,10 @@ } switch (mech->mechanism) { + case CKM_MD5_HMAC_GENERAL: + case CKM_MD5_HMAC: + rc = EVP_DigestSignInit(mdctx, NULL, EVP_md5(), NULL, pkey); + break; case CKM_SHA_1_HMAC_GENERAL: case CKM_SHA_1_HMAC: rc = EVP_DigestSignInit(mdctx, NULL, EVP_sha1(), NULL, pkey); @@ -4306,6 +4530,8 @@ goto done; } else { ctx->context = (CK_BYTE *) mdctx; + ctx->context_free_func = openssl_specific_hmac_free; + ctx->state_unsaveable = TRUE; } rc = CKR_OK; @@ -4340,6 +4566,12 @@ } switch (ctx->mech.mechanism) { + case CKM_MD5_HMAC_GENERAL: + general = TRUE; + /* fallthrough */ + case CKM_MD5_HMAC: + mac_len = MD5_HASH_SIZE; + break; case CKM_SHA_1_HMAC_GENERAL: general = TRUE; /* fallthrough */ @@ -4468,7 +4700,6 @@ TRACE_ERROR("EVP_DigestSignUpdate failed.\n"); rv = CKR_FUNCTION_FAILED; } else { - ctx->context = (CK_BYTE *) mdctx; return CKR_OK; } @@ -4496,6 +4727,12 @@ } switch (ctx->mech.mechanism) { + case CKM_MD5_HMAC_GENERAL: + general = TRUE; + /* fallthrough */ + case CKM_MD5_HMAC: + mac_len = MD5_HASH_SIZE; + break; case CKM_SHA_1_HMAC_GENERAL: general = TRUE; /* fallthrough */ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_rsa.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_rsa.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_rsa.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_rsa.c 2023-02-13 09:22:42.000000000 +0100 @@ -1775,12 +1775,14 @@ memset(&digest_ctx, 0x0, sizeof(digest_ctx)); memset(&sign_ctx, 0x0, sizeof(sign_ctx)); +#if !(NOMD2) if (ctx->mech.mechanism == CKM_MD2_RSA_PKCS) { digest_mech.mechanism = CKM_MD2; oid = ber_AlgMd2; oid_len = ber_AlgMd2Len; - - } else if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) { + } else +#endif + if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) { digest_mech.mechanism = CKM_MD5; oid = ber_AlgMd5; oid_len = ber_AlgMd5Len; @@ -1887,9 +1889,12 @@ context = (RSA_DIGEST_CONTEXT *) ctx->context; if (context->flag == FALSE) { +#if !(NOMD2) if (ctx->mech.mechanism == CKM_MD2_RSA_PKCS) digest_mech.mechanism = CKM_MD2; - else if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) + else +#endif + if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) digest_mech.mechanism = CKM_MD5; else if (ctx->mech.mechanism == CKM_SHA224_RSA_PKCS) digest_mech.mechanism = CKM_SHA224; @@ -1956,11 +1961,14 @@ memset(&digest_ctx, 0x0, sizeof(digest_ctx)); memset(&verify_ctx, 0x0, sizeof(verify_ctx)); +#if !(NOMD2) if (ctx->mech.mechanism == CKM_MD2_RSA_PKCS) { digest_mech.mechanism = CKM_MD2; oid = ber_AlgMd2; oid_len = ber_AlgMd2Len; - } else if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) { + } else +#endif + if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) { digest_mech.mechanism = CKM_MD5; oid = ber_AlgMd5; oid_len = ber_AlgMd5Len; @@ -2065,9 +2073,12 @@ context = (RSA_DIGEST_CONTEXT *) ctx->context; if (context->flag == FALSE) { +#if !(NOMD2) if (ctx->mech.mechanism == CKM_MD2_RSA_PKCS) digest_mech.mechanism = CKM_MD2; - else if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) + else +#endif + if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) digest_mech.mechanism = CKM_MD5; else if (ctx->mech.mechanism == CKM_SHA224_RSA_PKCS) digest_mech.mechanism = CKM_SHA224; @@ -2131,10 +2142,13 @@ return CKR_FUNCTION_FAILED; } +#if !(NOMD2) if (ctx->mech.mechanism == CKM_MD2_RSA_PKCS) { oid = ber_AlgMd2; oid_len = ber_AlgMd2Len; - } else if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) { + } else +#endif + if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) { oid = ber_AlgMd5; oid_len = ber_AlgMd5Len; } else if (ctx->mech.mechanism == CKM_SHA224_RSA_PKCS) { @@ -2247,10 +2261,13 @@ TRACE_ERROR("%s received bad argument(s)\n", __func__); return CKR_FUNCTION_FAILED; } +#if !(NOMD2) if (ctx->mech.mechanism == CKM_MD2_RSA_PKCS) { oid = ber_AlgMd2; oid_len = ber_AlgMd2Len; - } else if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) { + } else +#endif + if (ctx->mech.mechanism == CKM_MD5_RSA_PKCS) { oid = ber_AlgMd5; oid_len = ber_AlgMd5Len; } else if (ctx->mech.mechanism == CKM_SHA224_RSA_PKCS) { @@ -2584,7 +2601,7 @@ error++; ps_len = hlen; - while ((dbMask[ps_len] == 0x00) && (ps_len < dbMask_len)) + while ((ps_len < dbMask_len) && (dbMask[ps_len] == 0x00)) ps_len++; if ((ps_len >= dbMask_len) || @@ -2773,7 +2790,7 @@ /* pkcs1v2.2, Step 10: check DB. */ i = 0; plen = emLen - hlen - pssParms->sLen - 2; - while ((buf[i] == 0) && (i < plen)) + while ((i < plen) && (buf[i] == 0)) i++; if ((i != plen) || (buf[i++] != 0x01)) { diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_sha.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_sha.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_sha.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_sha.c 2023-02-13 09:22:42.000000000 +0100 @@ -369,16 +369,9 @@ CK_ULONG in_data_len, CK_BYTE *out_data, CK_ULONG *out_data_len) { - OBJECT *key_obj = NULL; - CK_ATTRIBUTE *attr = NULL; - CK_BYTE hash[MAX_SHA_HASH_SIZE]; - DIGEST_CONTEXT digest_ctx; CK_MECHANISM digest_mech; - CK_BYTE k_ipad[MAX_SHA_BLOCK_SIZE]; - CK_BYTE k_opad[MAX_SHA_BLOCK_SIZE]; - CK_ULONG key_bytes, hash_len, hmac_len, digest_hash_len, digest_block_size; + CK_ULONG hmac_len, digest_hash_len, digest_block_size; CK_BBOOL general = FALSE; - CK_ULONG i; CK_RV rc; if (!sess || !ctx || !out_data_len) { @@ -428,137 +421,8 @@ return token_specific.t_hmac_sign(tokdata, sess, in_data, in_data_len, out_data, out_data_len); - /* Do manual hmac if token doesn't have an hmac crypto call. - * Secure tokens should not do manual hmac. - */ - - memset(&digest_ctx, 0x0, sizeof(DIGEST_CONTEXT)); - - rc = object_mgr_find_in_map1(tokdata, ctx->key, &key_obj, READ_LOCK); - if (rc != CKR_OK) { - TRACE_ERROR("Failed to acquire key from specified handle.\n"); - if (rc == CKR_OBJECT_HANDLE_INVALID) - return CKR_KEY_HANDLE_INVALID; - else - return rc; - } - - rc = template_attribute_get_non_empty(key_obj->template, CKA_VALUE, &attr); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_VALUE in the template\n"); - goto done; - } - - key_bytes = attr->ulValueLen; - - // build (K XOR ipad), (K XOR opad) - // - if (key_bytes > digest_block_size) { - rc = digest_mgr_init(tokdata, sess, &digest_ctx, &digest_mech, FALSE); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Init failed.\n"); - goto done; - } - - hash_len = digest_hash_len; - rc = digest_mgr_digest(tokdata, sess, FALSE, &digest_ctx, - attr->pValue, attr->ulValueLen, hash, &hash_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Digest failed.\n"); - digest_mgr_cleanup(tokdata, sess, &digest_ctx); - goto done; - } - - memset(&digest_ctx, 0x0, sizeof(DIGEST_CONTEXT)); - - for (i = 0; i < hash_len; i++) { - k_ipad[i] = hash[i] ^ 0x36; - k_opad[i] = hash[i] ^ 0x5C; - } - - memset(&k_ipad[i], 0x36, digest_block_size - i); - memset(&k_opad[i], 0x5C, digest_block_size - i); - } else { - CK_BYTE *key = attr->pValue; - - for (i = 0; i < key_bytes; i++) { - k_ipad[i] = key[i] ^ 0x36; - k_opad[i] = key[i] ^ 0x5C; - } - - memset(&k_ipad[i], 0x36, digest_block_size - key_bytes); - memset(&k_opad[i], 0x5C, digest_block_size - key_bytes); - } - - // inner hash - // - rc = digest_mgr_init(tokdata, sess, &digest_ctx, &digest_mech, FALSE); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Init failed.\n"); - goto done; - } - - rc = digest_mgr_digest_update(tokdata, sess, &digest_ctx, k_ipad, - digest_block_size); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Update failed.\n"); - goto done; - } - - rc = digest_mgr_digest_update(tokdata, sess, &digest_ctx, in_data, - in_data_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Update failed.\n"); - goto done; - } - - hash_len = digest_hash_len; - rc = digest_mgr_digest_final(tokdata, sess, FALSE, &digest_ctx, hash, - &hash_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Final failed.\n"); - goto done; - } - - memset(&digest_ctx, 0x0, sizeof(DIGEST_CONTEXT)); - - // outer hash - // - rc = digest_mgr_init(tokdata, sess, &digest_ctx, &digest_mech, FALSE); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Init failed.\n"); - goto done; - } - - rc = digest_mgr_digest_update(tokdata, sess, &digest_ctx, k_opad, - digest_block_size); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Update failed.\n"); - goto done; - } - - rc = digest_mgr_digest_update(tokdata, sess, &digest_ctx, hash, hash_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Update failed.\n"); - goto done; - } - - hash_len = digest_hash_len; - rc = digest_mgr_digest_final(tokdata, sess, FALSE, &digest_ctx, hash, - &hash_len); - if (rc != CKR_OK) { - TRACE_DEVEL("Digest Mgr Final failed.\n"); - goto done; - } - - memcpy(out_data, hash, hmac_len); - *out_data_len = hmac_len; - -done: - object_put(tokdata, key_obj, TRUE); - key_obj = NULL; - - return rc; + return openssl_specific_hmac(&sess->sign_ctx, in_data, in_data_len, + out_data, out_data_len, TRUE); } // this routine gets called for these mechanisms actually: @@ -586,12 +450,6 @@ CK_BYTE *in_data, CK_ULONG in_data_len, CK_BYTE *signature, CK_ULONG sig_len) { - CK_BYTE hmac[MAX_SHA_HASH_SIZE]; - SIGN_VERIFY_CONTEXT hmac_ctx; - CK_ULONG hmac_len, len, digest_mech, digest_hash_len; - CK_BBOOL general = FALSE; - CK_RV rc; - if (!sess || !ctx || !in_data || !signature) { TRACE_ERROR("%s received bad argument(s)\n", __func__); return CKR_FUNCTION_FAILED; @@ -601,75 +459,17 @@ return token_specific.t_hmac_verify(tokdata, sess, in_data, in_data_len, signature, sig_len); - /* Do manual hmac verify if token doesn't have an hmac crypto call. - * Secure tokens should not do manual hmac. - */ - - rc = get_hmac_digest(ctx->mech.mechanism, &digest_mech, &general); - if (rc != 0) { - TRACE_ERROR("get_hmac_digest failed"); - return rc; - } - - rc = get_sha_size(digest_mech, &digest_hash_len); - if (rc != 0) { - TRACE_ERROR("get_sha_size failed"); - return rc; - } - - if (general == FALSE) { - hmac_len = digest_hash_len; - } else { - hmac_len = *(CK_ULONG *)ctx->mech.pParameter; - if (hmac_len > digest_hash_len) - return CKR_MECHANISM_PARAM_INVALID; - } - - memset(&hmac_ctx, 0, sizeof(SIGN_VERIFY_CONTEXT)); - - rc = sign_mgr_init(tokdata, sess, &hmac_ctx, &ctx->mech, FALSE, ctx->key, - FALSE); - if (rc != CKR_OK) { - TRACE_DEVEL("Sign Mgr Init failed.\n"); - goto done; - } - len = hmac_len; - rc = sign_mgr_sign(tokdata, sess, FALSE, &hmac_ctx, in_data, in_data_len, - hmac, &len); - if (rc != CKR_OK) { - TRACE_DEVEL("Sign Mgr Sign failed.\n"); - goto done; - } - if ((len != hmac_len) || (len != sig_len)) { - TRACE_ERROR("%s\n", ock_err(ERR_SIGNATURE_LEN_RANGE)); - rc = CKR_SIGNATURE_LEN_RANGE; - goto done; - } - - if (CRYPTO_memcmp(hmac, signature, hmac_len) != 0) { - TRACE_ERROR("%s\n", ock_err(ERR_SIGNATURE_INVALID)); - rc = CKR_SIGNATURE_INVALID; - } - -done: - sign_mgr_cleanup(tokdata, sess, &hmac_ctx); - return rc; + return openssl_specific_hmac(&sess->verify_ctx, in_data, in_data_len, + signature, &sig_len, FALSE); } - - CK_RV hmac_sign_init(STDLL_TokData_t *tokdata, SESSION *sess, CK_MECHANISM *mech, CK_OBJECT_HANDLE hkey) { if (token_specific.t_hmac_sign_init != NULL) return token_specific.t_hmac_sign_init(tokdata, sess, mech, hkey); - /* Return ok with the intention that the local hmac - * implementation will get used instead. - * For those tokens not supporting HMAC at all, - * will need to return CKR_MECHANISM_INVALID. - */ - return CKR_OK; + return openssl_specific_hmac_init(tokdata, &sess->sign_ctx, mech, hkey); } CK_RV hmac_sign_update(STDLL_TokData_t *tokdata, SESSION *sess, @@ -686,9 +486,8 @@ return token_specific.t_hmac_sign_update(tokdata, sess, in_data, in_data_len); - TRACE_ERROR("hmac-update is not supported\n"); - - return CKR_MECHANISM_INVALID; + return openssl_specific_hmac_update(&sess->sign_ctx, in_data, in_data_len, + TRUE); } CK_RV hmac_sign_final(STDLL_TokData_t *tokdata, SESSION *sess, @@ -705,9 +504,8 @@ return token_specific.t_hmac_sign_final(tokdata, sess, signature, sig_len); - TRACE_ERROR("hmac-final is not supported\n"); - - return CKR_MECHANISM_INVALID; + return openssl_specific_hmac_final(&sess->sign_ctx, signature, sig_len, + TRUE); } CK_RV hmac_verify_init(STDLL_TokData_t *tokdata, SESSION *sess, @@ -716,12 +514,7 @@ if (token_specific.t_hmac_verify_init != NULL) return token_specific.t_hmac_verify_init(tokdata, sess, mech, hkey); - /* Return ok with the intention that the local hmac - * implementation will get used instead. - * For those tokens not supporting HMAC at all, - * will need to return CKR_MECHANISM_INVALID. - */ - return CKR_OK; + return openssl_specific_hmac_init(tokdata, &sess->verify_ctx, mech, hkey); } CK_RV hmac_verify_update(STDLL_TokData_t *tokdata, SESSION *sess, @@ -738,9 +531,8 @@ return token_specific.t_hmac_verify_update(tokdata, sess, in_data, in_data_len); - TRACE_ERROR("hmac-update is not supported\n"); - - return CKR_MECHANISM_INVALID; + return openssl_specific_hmac_update(&sess->verify_ctx, in_data, in_data_len, + FALSE); } CK_RV hmac_verify_final(STDLL_TokData_t *tokdata, SESSION *sess, @@ -757,9 +549,8 @@ return token_specific.t_hmac_verify_final(tokdata, sess, signature, sig_len); - TRACE_ERROR("hmac-final is not supported\n"); - - return CKR_MECHANISM_INVALID; + return openssl_specific_hmac_final(&sess->verify_ctx, signature, &sig_len, + FALSE); } CK_RV ckm_generic_secret_key_gen(STDLL_TokData_t *tokdata, TEMPLATE *tmpl) diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/mech_ssl3.c opencryptoki-3.20.0+dfsg/usr/lib/common/mech_ssl3.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/mech_ssl3.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/mech_ssl3.c 2023-02-13 09:22:42.000000000 +0100 @@ -1954,16 +1954,11 @@ } switch (keytype) { case CKK_AES: + case CKK_AES_XTS: case CKK_GENERIC_SECRET: case CKK_DES: case CKK_DES2: case CKK_DES3: - case CKK_RC2: - case CKK_RC4: - case CKK_RC5: - case CKK_CAST: - case CKK_CAST3: - case CKK_CAST5: rc = build_attribute(CKA_VALUE_LEN, (CK_BYTE *) & write_len, sizeof(CK_ULONG), &client_val_len_attr); rc |= diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/new_host.c opencryptoki-3.20.0+dfsg/usr/lib/common/new_host.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/new_host.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/new_host.c 2023-02-13 09:22:42.000000000 +0100 @@ -508,7 +508,7 @@ CK_FLAGS_32 *flags = NULL; TOKEN_DATA_VERSION *dat; unsigned char login_key[32], wrap_key[32], login_salt[64], wrap_salt[64]; - uint64_t login_it, wrap_it; + uint64_t login_it = 0, wrap_it = 0; if (tokdata->initialized == FALSE) { TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); @@ -1141,7 +1141,7 @@ goto done; } - rc = session_mgr_get_op_state(sess, length_only, pOperationState, + rc = session_mgr_get_op_state(tokdata, sess, length_only, pOperationState, pulOperationStateLen); if (rc != CKR_OK) TRACE_DEVEL("session_mgr_get_op_state() failed.\n"); @@ -1203,6 +1203,35 @@ return rc; } +CK_RV SC_SessionCancel(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, + CK_FLAGS flags) +{ + SESSION *sess = NULL; + CK_RV rc = CKR_OK; + + if (tokdata->initialized == FALSE) { + TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); + rc = CKR_CRYPTOKI_NOT_INITIALIZED; + goto done; + } + + sess = session_mgr_find(tokdata, sSession->sessionh); + if (!sess) { + TRACE_ERROR("%s\n", ock_err(ERR_SESSION_HANDLE_INVALID)); + rc = CKR_SESSION_HANDLE_INVALID; + goto done; + } + + rc = session_mgr_cancel(tokdata, sess, flags); + +done: + TRACE_INFO("SC_SessionCancel: sess = %lu\n", sSession->sessionh); + + if (sess != NULL) + session_mgr_put(tokdata, sess); + + return rc; +} CK_RV SC_Login(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, CK_USER_TYPE userType, CK_CHAR_PTR pPin, CK_ULONG ulPinLen) @@ -1764,7 +1793,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); if (rc == CKR_OK && attr->ulValueLen != CK_UNAVAILABLE_INFORMATION) { @@ -1822,7 +1851,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -1887,7 +1916,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -3380,20 +3409,17 @@ CK_ULONG ulPartLen, CK_BYTE_PTR pEncryptedPart, CK_ULONG_PTR pulEncryptedPartLen) { - UNUSED(sSession); - UNUSED(pPart); - UNUSED(ulPartLen); - UNUSED(pEncryptedPart); - UNUSED(pulEncryptedPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_EncryptUpdate(tokdata, sSession, pPart, ulPartLen, + pEncryptedPart, pulEncryptedPartLen); + if (rc != CKR_OK || pEncryptedPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_DigestUpdate(tokdata, sSession, pPart, ulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -3403,20 +3429,17 @@ CK_ULONG ulEncryptedPartLen, CK_BYTE_PTR pPart, CK_ULONG_PTR pulPartLen) { - UNUSED(sSession); - UNUSED(pEncryptedPart); - UNUSED(ulEncryptedPartLen); - UNUSED(pPart); - UNUSED(pulPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_DecryptUpdate(tokdata, sSession, pEncryptedPart, + ulEncryptedPartLen, pPart, pulPartLen); + if (rc != CKR_OK || pPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_DigestUpdate(tokdata, sSession, pPart, *pulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -3425,43 +3448,36 @@ CK_ULONG ulPartLen, CK_BYTE_PTR pEncryptedPart, CK_ULONG_PTR pulEncryptedPartLen) { - UNUSED(sSession); - UNUSED(pPart); - UNUSED(ulPartLen); - UNUSED(pEncryptedPart); - UNUSED(pulEncryptedPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_EncryptUpdate(tokdata, sSession, pPart, ulPartLen, + pEncryptedPart, pulEncryptedPartLen); + if (rc != CKR_OK || pEncryptedPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_SignUpdate(tokdata, sSession, pPart, ulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } - CK_RV SC_DecryptVerifyUpdate(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, CK_BYTE_PTR pEncryptedPart, CK_ULONG ulEncryptedPartLen, CK_BYTE_PTR pPart, CK_ULONG_PTR pulPartLen) { - UNUSED(sSession); - UNUSED(pEncryptedPart); - UNUSED(ulEncryptedPartLen); - UNUSED(pPart); - UNUSED(pulPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_DecryptUpdate(tokdata, sSession, pEncryptedPart, + ulEncryptedPartLen, pPart, pulPartLen); + if (rc != CKR_OK || pPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_VerifyUpdate(tokdata, sSession, pPart, *pulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -3527,7 +3543,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -3624,13 +3640,13 @@ TRACE_DEBUG("Public Template:\n"); attr = pPublicKeyTemplate; - for (i = 0; i < ulPublicKeyAttributeCount; i++, attr++) { + for (i = 0; i < ulPublicKeyAttributeCount && attr != NULL; i++, attr++) { TRACE_DEBUG_DUMPATTR(attr); } TRACE_DEBUG("Private Template:\n"); attr = pPrivateKeyTemplate; - for (i = 0; i < ulPrivateKeyAttributeCount; i++, attr++) { + for (i = 0; i < ulPrivateKeyAttributeCount && attr != NULL; i++, attr++) { TRACE_DEBUG_DUMPATTR(attr); } #endif @@ -3759,7 +3775,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -3863,7 +3879,7 @@ } attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -3923,6 +3939,9 @@ goto done; } + if (ulRandomLen == 0) + goto done; + rc = rng_generate(tokdata, pRandomData, ulRandomLen); if (rc != CKR_OK) TRACE_DEVEL("rng_generate() failed.\n"); @@ -4109,10 +4128,10 @@ function_list.ST_VerifyFinal = SC_VerifyFinal; function_list.ST_VerifyRecoverInit = SC_VerifyRecoverInit; function_list.ST_VerifyRecover = SC_VerifyRecover; - function_list.ST_DigestEncryptUpdate = NULL; // SC_DigestEncryptUpdate; - function_list.ST_DecryptDigestUpdate = NULL; // SC_DecryptDigestUpdate; - function_list.ST_SignEncryptUpdate = NULL; //SC_SignEncryptUpdate; - function_list.ST_DecryptVerifyUpdate = NULL; // SC_DecryptVerifyUpdate; + function_list.ST_DigestEncryptUpdate = SC_DigestEncryptUpdate; + function_list.ST_DecryptDigestUpdate = SC_DecryptDigestUpdate; + function_list.ST_SignEncryptUpdate = SC_SignEncryptUpdate; + function_list.ST_DecryptVerifyUpdate = SC_DecryptVerifyUpdate; function_list.ST_GenerateKey = SC_GenerateKey; function_list.ST_GenerateKeyPair = SC_GenerateKeyPair; function_list.ST_WrapKey = SC_WrapKey; @@ -4122,6 +4141,7 @@ function_list.ST_GenerateRandom = SC_GenerateRandom; function_list.ST_GetFunctionStatus = NULL; // SC_GetFunctionStatus; function_list.ST_CancelFunction = NULL; // SC_CancelFunction; + function_list.ST_SessionCancel = SC_SessionCancel; function_list.ST_IBM_ReencryptSingle = SC_IBM_ReencryptSingle; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/object.c opencryptoki-3.20.0+dfsg/usr/lib/common/object.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/object.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/object.c 2023-02-13 09:22:42.000000000 +0100 @@ -140,7 +140,7 @@ // // The old_obj must hold the READ lock! // -CK_RV object_copy(STDLL_TokData_t * tokdata, +CK_RV object_copy(STDLL_TokData_t * tokdata, SESSION *sess, CK_ATTRIBUTE * pTemplate, CK_ULONG ulCount, OBJECT * old_obj, OBJECT ** new_obj) { @@ -228,7 +228,7 @@ * changed. */ if (token_specific.t_set_attribute_values != NULL) { - rc = token_specific.t_set_attribute_values(tokdata, o, new_tmpl); + rc = token_specific.t_set_attribute_values(tokdata, sess, o, new_tmpl); if (rc != CKR_OK) { TRACE_DEVEL("token_specific_set_attribute_values failed with %lu\n", rc); @@ -620,7 +620,7 @@ // object_set_attribute_values() // -CK_RV object_set_attribute_values(STDLL_TokData_t * tokdata, +CK_RV object_set_attribute_values(STDLL_TokData_t * tokdata, SESSION *sess, OBJECT * obj, CK_ATTRIBUTE * pTemplate, CK_ULONG ulCount) { @@ -669,7 +669,8 @@ } if (token_specific.t_set_attribute_values != NULL) { - rc = token_specific.t_set_attribute_values(tokdata, obj, new_tmpl); + rc = token_specific.t_set_attribute_values(tokdata, sess, + obj, new_tmpl); if (rc != CKR_OK) { TRACE_DEVEL("token_specific_set_attribute_values failed with %lu\n", rc); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/obj_mgr.c opencryptoki-3.20.0+dfsg/usr/lib/common/obj_mgr.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/obj_mgr.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/obj_mgr.c 2023-02-13 09:22:42.000000000 +0100 @@ -87,7 +87,7 @@ CK_ULONG ulCount, CK_OBJECT_HANDLE *handle) { OBJECT *o = NULL; - CK_BBOOL priv_obj, sess_obj, locked = FALSE; + CK_BBOOL priv_obj, sess_obj; CK_RV rc; CK_OBJECT_CLASS class; CK_KEY_TYPE keytype; @@ -123,6 +123,11 @@ switch(class) { case CKO_PUBLIC_KEY: case CKO_PRIVATE_KEY: + /* Skip if there is already a non-empty CKA_PUBLIC_KEY_INFO */ + if (template_attribute_get_non_empty(o->template, CKA_PUBLIC_KEY_INFO, + &spki_attr) == CKR_OK) + break; + rc = template_attribute_get_ulong(o->template, CKA_KEY_TYPE, &keytype); if (rc != CKR_OK) { TRACE_ERROR("Could not find CKA_KEY_TYPE for the key object.\n"); @@ -160,6 +165,7 @@ switch (keytype) { case CKK_GENERIC_SECRET: case CKK_AES: + case CKK_AES_XTS: rc = template_attribute_get_non_empty(o->template, CKA_VALUE, &value_attr); if (rc != CKR_OK) { @@ -208,18 +214,6 @@ if (spki != NULL) free(spki); - if (locked) { - if (rc == CKR_OK) { - rc = XProcUnLock(tokdata); - if (rc != CKR_OK) { - TRACE_ERROR("Failed to release Process Lock.\n"); - } - } else { - /* return error that occurred first */ - XProcUnLock(tokdata); - } - } - if (rc == CKR_OK) TRACE_DEVEL("Object created: handle: %lu\n", *handle); @@ -304,7 +298,6 @@ OBJECT *new_obj = NULL; CK_BBOOL priv_obj; CK_BBOOL sess_obj; - CK_BBOOL locked = FALSE; CK_RV rc; if (!sess || (!pTemplate && ulCount) || !new_handle) { @@ -324,7 +317,7 @@ goto done; } - rc = object_copy(tokdata, pTemplate, ulCount, old_obj, &new_obj); + rc = object_copy(tokdata, sess, pTemplate, ulCount, old_obj, &new_obj); if (rc != CKR_OK) { TRACE_DEVEL("Object Copy failed.\n"); goto done; @@ -350,19 +343,6 @@ object_put(tokdata, old_obj, TRUE); old_obj = NULL; - if (locked) { - if (rc == CKR_OK) { - rc = XProcUnLock(tokdata); - if (rc != CKR_OK) { - TRACE_ERROR("Failed to release Process Lock.\n"); - goto done; - } - } else { - /* return error that occurred first */ - XProcUnLock(tokdata); - } - } - return rc; } @@ -697,14 +677,6 @@ } done: - if (o != NULL) { - if (map->is_private) - bt_put_node_value(&tokdata->priv_token_obj_btree, o); - else - bt_put_node_value(&tokdata->publ_token_obj_btree, o); - o = NULL; - } - bt_put_node_value(&tokdata->object_map_btree, map); if (locked) { @@ -977,9 +949,9 @@ } rc = object_unlock(obj); + locked = FALSE; if (rc != CKR_OK) goto done; - locked = FALSE; } rc = object_lock(obj, lock_type); @@ -1167,8 +1139,8 @@ return CKR_FUNCTION_FAILED; } if (sess->find_active != FALSE) { - return CKR_OPERATION_ACTIVE; TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_ACTIVE)); + return CKR_OPERATION_ACTIVE; } // initialize the found object list. if it doesn't exist, allocate // a list big enough for 10 handles. we'll reallocate if we need more @@ -1472,6 +1444,7 @@ OBJECT *obj = NULL; CK_BBOOL priv; CK_RV rc, tmp; + TOK_OBJ_ENTRY *entry = NULL; if (!data) { TRACE_ERROR("Invalid function argument.\n"); @@ -1480,70 +1453,90 @@ // The calling stack MUST have the mutex // to many grab it now. + obj = oldObj; + rc = object_restore_withSize(tokdata->policy, + data, &obj, oldObj != NULL, data_size, fname); + if (rc != CKR_OK) { + TRACE_DEVEL("object_restore_withSize failed.\n"); + return rc; + } + + rc = XProcLock(tokdata); + if (rc != CKR_OK) { + TRACE_ERROR("Failed to get Process Lock.\n"); + object_free(obj); + return rc; + } + if (oldObj != NULL) { - obj = oldObj; - rc = object_restore_withSize(tokdata->policy, - data, &obj, TRUE, data_size, fname); - } else { - rc = object_restore_withSize(tokdata->policy, - data, &obj, FALSE, data_size, fname); + /* Update of existing object */ + rc = object_mgr_get_shm_entry_for_obj(tokdata, obj, &entry); if (rc == CKR_OK) { - rc = XProcLock(tokdata); - if (rc != CKR_OK) { - TRACE_ERROR("Failed to get Process Lock.\n"); + obj->count_lo = entry->count_lo; + obj->count_hi = entry->count_hi; + } + } else { + /* New object */ + priv = object_is_private(obj); + + if (priv) { + if (!bt_node_add(&tokdata->priv_token_obj_btree, obj)) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; object_free(obj); - return rc; + goto unlock; } + } else { + if (!bt_node_add(&tokdata->publ_token_obj_btree, obj)) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + object_free(obj); + goto unlock; + } + } - priv = object_is_private(obj); - - if (priv) { - if (!bt_node_add(&tokdata->priv_token_obj_btree, obj)) { + if (priv) { + if (tokdata->global_shm->priv_loaded == FALSE) { + if (tokdata->global_shm->num_priv_tok_obj < MAX_TOK_OBJS) { + object_mgr_add_to_shm(obj, tokdata->global_shm); + } else { TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); rc = CKR_HOST_MEMORY; - object_free(obj); goto unlock; } } else { - if (!bt_node_add(&tokdata->publ_token_obj_btree, obj)) { + rc = object_mgr_get_shm_entry_for_obj(tokdata, obj, &entry); + if (rc == CKR_OK) { + obj->count_lo = entry->count_lo; + obj->count_hi = entry->count_hi; + } + } + } else { + if (tokdata->global_shm->publ_loaded == FALSE) { + if (tokdata->global_shm->num_publ_tok_obj < MAX_TOK_OBJS) { + object_mgr_add_to_shm(obj, tokdata->global_shm); + } else { TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); rc = CKR_HOST_MEMORY; - object_free(obj); goto unlock; } - } - - if (priv) { - if (tokdata->global_shm->priv_loaded == FALSE) { - if (tokdata->global_shm->num_priv_tok_obj < MAX_TOK_OBJS) { - object_mgr_add_to_shm(obj, tokdata->global_shm); - } else { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - } - } } else { - if (tokdata->global_shm->publ_loaded == FALSE) { - if (tokdata->global_shm->num_publ_tok_obj < MAX_TOK_OBJS) { - object_mgr_add_to_shm(obj, tokdata->global_shm); - } else { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - rc = CKR_HOST_MEMORY; - } + rc = object_mgr_get_shm_entry_for_obj(tokdata, obj, &entry); + if (rc == CKR_OK) { + obj->count_lo = entry->count_lo; + obj->count_hi = entry->count_hi; } } - -unlock: - tmp = XProcUnLock(tokdata); - if (tmp != CKR_OK) - TRACE_ERROR("Failed to release Process Lock.\n"); - if (rc == CKR_OK) - rc = tmp; - } else { - TRACE_DEVEL("object_restore_withSize failed.\n"); } } +unlock: + tmp = XProcUnLock(tokdata); + if (tmp != CKR_OK) + TRACE_ERROR("Failed to release Process Lock.\n"); + if (rc == CKR_OK) + rc = tmp; + return rc; } @@ -1670,7 +1663,7 @@ if (rc != CKR_OK) goto done; - rc = object_set_attribute_values(tokdata, obj, pTemplate, ulCount); + rc = object_set_attribute_values(tokdata, sess, obj, pTemplate, ulCount); if (rc != CKR_OK) { TRACE_DEVEL("object_set_attribute_values failed.\n"); goto done; @@ -1828,31 +1821,19 @@ return CKR_OK; } - -// The object must hold the READ lock when this function is called! -// -CK_RV object_mgr_check_shm(STDLL_TokData_t *tokdata, OBJECT *obj) +CK_RV object_mgr_get_shm_entry_for_obj(STDLL_TokData_t *tokdata, OBJECT *obj, + TOK_OBJ_ENTRY **entry) { - TOK_OBJ_ENTRY *entry = NULL; - CK_BBOOL priv, rd_locked = TRUE, wr_locked = FALSE; CK_ULONG index; CK_RV rc; - priv = object_is_private(obj); + *entry = NULL; -retry: - rc = XProcLock(tokdata); - if (rc != CKR_OK) { - TRACE_ERROR("Failed to get Process Lock.\n"); - goto done_no_xproc_unlock; - } - - if (priv) { + if (object_is_private(obj)) { /* first check the object count. If it is 0, then just return. */ if (tokdata->global_shm->num_priv_tok_obj == 0) { TRACE_ERROR("%s\n", ock_err(ERR_OBJECT_HANDLE_INVALID)); - rc = CKR_OBJECT_HANDLE_INVALID; - goto done; + return CKR_OBJECT_HANDLE_INVALID; } rc = object_mgr_search_shm_for_obj(tokdata->global_shm->priv_tok_objs, 0, @@ -1860,15 +1841,14 @@ num_priv_tok_obj - 1, obj, &index); if (rc != CKR_OK) { TRACE_ERROR("object_mgr_search_shm_for_obj failed.\n"); - goto done; + return rc; } - entry = &tokdata->global_shm->priv_tok_objs[index]; + *entry = &tokdata->global_shm->priv_tok_objs[index]; } else { /* first check the object count. If it is 0, then just return. */ if (tokdata->global_shm->num_publ_tok_obj == 0) { TRACE_ERROR("%s\n", ock_err(ERR_OBJECT_HANDLE_INVALID)); - rc = CKR_OBJECT_HANDLE_INVALID; - goto done; + return CKR_OBJECT_HANDLE_INVALID; } rc = object_mgr_search_shm_for_obj(tokdata->global_shm->publ_tok_objs, 0, @@ -1877,11 +1857,34 @@ obj, &index); if (rc != CKR_OK) { TRACE_ERROR("object_mgr_search_shm_for_obj failed.\n"); - goto done; + return rc; } - entry = &tokdata->global_shm->publ_tok_objs[index]; + *entry = &tokdata->global_shm->publ_tok_objs[index]; + } + + return CKR_OK; +} + + +// The object must hold the READ lock when this function is called! +// +CK_RV object_mgr_check_shm(STDLL_TokData_t *tokdata, OBJECT *obj) +{ + TOK_OBJ_ENTRY *entry = NULL; + CK_BBOOL rd_locked = TRUE, wr_locked = FALSE; + CK_RV rc; + +retry: + rc = XProcLock(tokdata); + if (rc != CKR_OK) { + TRACE_ERROR("Failed to get Process Lock.\n"); + goto done_no_xproc_unlock; } + rc = object_mgr_get_shm_entry_for_obj(tokdata, obj, &entry); + if (rc != CKR_OK) + goto done; + if ((obj->count_hi == entry->count_hi) && (obj->count_lo == entry->count_lo)) { rc = CKR_OK; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/p11util.c opencryptoki-3.20.0+dfsg/usr/lib/common/p11util.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/p11util.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/p11util.c 2023-02-13 09:22:42.000000000 +0100 @@ -123,6 +123,10 @@ } } +#ifndef CKA_IBM_PQC_PARAMS +#define CKA_IBM_PQC_PARAMS (CKA_VENDOR_DEFINED +0x1000e) +#endif + // // p11_get_cka - return textual interpretation of an attribute type // only simple types - no arrays. For unknown a ptr to a static @@ -221,6 +225,7 @@ _sym2str(CKA_IBM_PROTKEY_NEVER_EXTRACTABLE); _sym2str(CKA_IBM_OPAQUE_PKEY); _sym2str(CKA_IBM_DILITHIUM_KEYFORM); + _sym2str(CKA_IBM_DILITHIUM_MODE); _sym2str(CKA_IBM_DILITHIUM_RHO); _sym2str(CKA_IBM_DILITHIUM_SEED); _sym2str(CKA_IBM_DILITHIUM_TR); @@ -228,6 +233,11 @@ _sym2str(CKA_IBM_DILITHIUM_S2); _sym2str(CKA_IBM_DILITHIUM_T0); _sym2str(CKA_IBM_DILITHIUM_T1); + _sym2str(CKA_IBM_PQC_PARAMS); + _sym2str(CKA_IBM_KYBER_KEYFORM); + _sym2str(CKA_IBM_KYBER_MODE); + _sym2str(CKA_IBM_KYBER_PK); + _sym2str(CKA_IBM_KYBER_SK); default: sprintf(buf, "unknown attribute type 0x%08lx", atype); return buf; @@ -417,3 +427,17 @@ } } } + +/* p11_strlen() - calculate the length of CK_CHAR field, which + * are not '\0' terminated but padded with spaces. + * @s is a pointer to a CK_CHAR string. + * @max_len is its maximum length. + */ +size_t p11_strlen(const CK_CHAR *s, size_t max_len) +{ + size_t len = max_len; + + while (len > 0 && s[len - 1] == ' ') + --len; + return len; +} diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/p11util.h opencryptoki-3.20.0+dfsg/usr/lib/common/p11util.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/p11util.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/p11util.h 2023-02-13 09:22:42.000000000 +0100 @@ -65,4 +65,11 @@ */ void p11_attribute_trim(CK_ATTRIBUTE *attr); +/* p11_strlen() - calculate the length of CK_CHAR field, which + * are not '\0' terminated but padded with spaces. + * @s is a pointer to a CK_CHAR string. + * @max_len is its maximum length. + */ +size_t p11_strlen(const CK_CHAR *s, size_t max_len); + #endif // #ifndef _P11UTIL_H_ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/pin_prompt.c opencryptoki-3.20.0+dfsg/usr/lib/common/pin_prompt.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/pin_prompt.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/pin_prompt.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,93 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#define _POSIX_C_SOURCE 200809L +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +static void echo(bool on) +{ + struct termios term; + + tcgetattr(fileno(stdin), &term); + + if (on) + term.c_lflag |= ECHO; + else + term.c_lflag &= ~ECHO; + + tcsetattr(fileno(stdin), TCSAFLUSH, &term); +} + +void pin_free(char **buf) +{ + if (!buf) + return; + + if (*buf) + OPENSSL_cleanse(*buf, strlen(*buf)); + + free(*buf); + *buf = NULL; +} + +const char *pin_prompt(char **buf, const char *msg) +{ + ssize_t n; + size_t s; + + if (!buf || *buf) + return NULL; + + printf("%s", msg); + fflush(stdout); + echo(false); + + n = getline(buf, &s, stdin); + + echo(true); + printf("\n"); + fflush(stdout); + + /* delayed getline() error handling */ + if (n == -1) + return NULL; + + /* strip on first occurence of CR/LF */ + (*buf)[strcspn(*buf, "\r\n")] = '\0'; + + return (const char *)*buf; +} + +const char *pin_prompt_new(char **buf, const char *msg1, const char *msg2) +{ + const char *pin = NULL; + char *buf2 = NULL; + + if (!pin_prompt(buf, msg1) || + !pin_prompt(&buf2, msg2)) + return NULL; + + if (strlen(*buf) && strlen(buf2) && + (!strcmp(*buf, buf2))) + pin = *buf; + + pin_free(&buf2); + + return pin; +} diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/pin_prompt.h opencryptoki-3.20.0+dfsg/usr/lib/common/pin_prompt.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/pin_prompt.h 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/pin_prompt.h 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,41 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#ifndef _PIN_PROMPT_H_ +#define _PIN_PROMPT_H_ + +void pin_free(char **buf); + +/** + * Print a message and prompt for input on stdin (echo is disabled during + * input). + * + * @param buf Pointer to a string (char *) for buffering the input. It must + * be free-ed after usage. + * @param msg Pointer to the prompt message. + * @returns Pointer to the input on success, otherwise NULL. The returned + * pointer must not be free-ed. + */ +const char *pin_prompt(char **buf, const char *msg); + +/** + * Prompt for a new pin twice and compare both inputs. + * + * @param buf Pointer to a string (char *) for buffering the input. It must + * be free-ed after usage. + * @param msg1 Pointer to the first prompt message. + * @param msg2 Pointer to the first prompt message. + * @returns Pointer to the pin on success (both inputs must be successful + * and both values must be equal), otherwise NULL. The returned + * pointer must not be free-ed. + */ +const char *pin_prompt_new(char **buf, const char *msg1, const char *msg2); + +#endif /* _PIN_PROMPT_H_ */ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/pkcs_utils.c opencryptoki-3.20.0+dfsg/usr/lib/common/pkcs_utils.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/pkcs_utils.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/pkcs_utils.c 2023-02-13 09:22:42.000000000 +0100 @@ -18,7 +18,6 @@ #include #include #include -#include #include #include #include @@ -86,7 +85,7 @@ printf("%s", buf); } -int compute_hash(int hash_type, int buf_size, char *buf, char *digest) +int compute_hash(int hash_type, int buf_size, const char *buf, char *digest) { EVP_MD_CTX *md_ctx = NULL; unsigned int result_size; @@ -262,68 +261,12 @@ return rc; } -int get_pin(char **pin, size_t *pinlen) -{ - struct termios old, new; - int nread; - char *buff = NULL; - size_t buflen; - int rc = 0; - - /* turn echoing off */ - if (tcgetattr(fileno(stdin), &old) != 0) - return -1; - - new = old; - new.c_lflag &= ~ECHO; - if (tcsetattr(fileno(stdin), TCSAFLUSH, &new) != 0) - return -1; - - /* read the pin - * Note: getline will allocate memory for buff. free it when done. - */ - nread = getline(&buff, &buflen, stdin); - if (nread == -1) { - rc = -1; - goto done; - } - - /* Restore terminal */ - (void) tcsetattr(fileno(stdin), TCSAFLUSH, &old); - - /* start a newline */ - printf("\n"); - fflush(stdout); - - /* Allocate PIN. - * Note: nread includes carriage return. - * Replace with terminating NULL. - */ - *pin = (char *) malloc(nread); - if (*pin == NULL) { - rc = -ENOMEM; - goto done; - } - - /* strip the carriage return since not part of pin. */ - buff[nread - 1] = '\0'; - memcpy(*pin, buff, nread); - /* don't include the terminating null in the pinlen */ - *pinlen = nread - 1; - -done: - if (buff) - free(buff); - - return rc; -} - /** * Verify that SO PIN and user PIN are correct by comparing their SHA-1 * values with the stored hashes in NVTOK.DAT. */ -int verify_pins(char *data_store, char *sopin, unsigned long sopinlen, - char *userpin, unsigned long userpinlen) +int verify_pins(char *data_store, const char *sopin, unsigned long sopinlen, + const char *userpin, unsigned long userpinlen) { TOKEN_DATA td; char fname[PATH_MAX]; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/pkcs_utils.h opencryptoki-3.20.0+dfsg/usr/lib/common/pkcs_utils.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/pkcs_utils.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/pkcs_utils.h 2023-02-13 09:22:42.000000000 +0100 @@ -26,7 +26,7 @@ #define compute_sha1(a,b,c) compute_hash((HASH_SHA1),(b),(a),(c)) #define compute_md5(a,b,c) compute_hash(HASH_MD5,(b),(a),(c)) -int compute_hash(int hash_type, int buf_size, char *buf, char *digest); +int compute_hash(int hash_type, int buf_size, const char *buf, char *digest); CK_RV local_rng(CK_BYTE *output, CK_ULONG bytes); @@ -42,10 +42,8 @@ const unsigned char key[32], const unsigned char iv[12]); -int get_pin(char **pin, size_t *pinlen); - -int verify_pins(char *data_store, char *sopin, unsigned long sopinlen, - char *userpin, unsigned long userpinlen); +int verify_pins(char *data_store, const char *sopin, unsigned long sopinlen, + const char *userpin, unsigned long userpinlen); void set_perm(int file); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/pkey_utils.c opencryptoki-3.20.0+dfsg/usr/lib/common/pkey_utils.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/pkey_utils.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/pkey_utils.c 2023-02-13 09:22:42.000000000 +0100 @@ -425,9 +425,13 @@ case CKM_AES_ECB: case CKM_AES_CBC: case CKM_AES_CBC_PAD: + if (msa_level > 1) + return CK_TRUE; + break; case CKM_AES_CMAC_GENERAL: case CKM_AES_CMAC: - if (msa_level > 1) + case CKM_AES_XTS: + if (msa_level > 3) return CK_TRUE; break; case CKM_ECDSA: @@ -749,6 +753,170 @@ return ret; } + +/** + * Return the KM/KMC/KMAC function code for the given key length and + * encrypt/decrypt op. + */ +unsigned long get_xts_function_code(CK_ULONG keylen, CK_BYTE encrypt) +{ + unsigned long fc; + + switch (keylen) { + case 32: + fc = ENCRYPTED_AES_XTS_128; + break; + case 64: + fc = ENCRYPTED_AES_XTS_256; + break; + default: + return 0; + } + + if (!encrypt) + fc |= CPACF_DECRYPT; + + return fc; +} + +/* compute protected key length [bytes] from key-size [bits] */ +#define AES_XTS_PROTKEYLEN(size) (32 + 16 * (size) / 128 ) +/* compute offsets [bytes] in PCC param structure from key-size [bits] */ +#define AES_XTS_PCC_I(size) (AES_XTS_PROTKEYLEN(size) + 0 * 16) +#define AES_XTS_PCC_XTSPARAM(size) (AES_XTS_PROTKEYLEN(size) + 3 * 16) +/* compute offsets [bytes] in KM param structure from key-size [bits] */ +#define AES_XTS_KM_XTSPARAM(size) (AES_XTS_PROTKEYLEN(size) + 0 * 16) + +/* parameter block for pcc compute for aes xts 256 */ +struct cpacf_pcc_xts_aes_256_param { + uint8_t protkey[64]; /* WKa(K)|WKaVP */ + uint8_t i[16]; + uint8_t j[16]; + uint8_t t[16]; + uint8_t xtsparams[16]; +}; + +/* parameter block for aes xts 256 */ +struct cpacf_km_xts_aes_256_param { + uint8_t protkey[64]; /* WKa(K)|WKaVP */ + uint8_t xtsparam[16]; +}; + +struct aes_xts_param { + uint8_t param_km[sizeof(struct cpacf_km_xts_aes_256_param)]; + uint8_t param_pcc[sizeof(struct cpacf_pcc_xts_aes_256_param)]; + unsigned int fc; + unsigned int keylen; +}; + +static CK_RV pkey_aes_xts_iv_from_tweak(CK_BYTE *tweak, CK_BYTE* iv, + void *cb_data) +{ + struct aes_xts_param *param = cb_data; + int offset, rc; + + offset = AES_XTS_PCC_I(param->keylen * 8); + memcpy(param->param_pcc + offset, tweak, AES_BLOCK_SIZE); + + rc = s390_pcc(param->fc & 0x7f, param->param_pcc); + if (rc < 0) { + TRACE_ERROR("s390_pcc function failed\n"); + return CKR_FUNCTION_FAILED; + } + + offset = AES_XTS_PCC_XTSPARAM(param->keylen * 8); + memcpy(iv, param->param_pcc + offset, AES_BLOCK_SIZE); + + return CKR_OK; +} + +static CK_RV pkey_aes_xts_cipher_blocks(CK_BYTE *in, CK_BYTE *out, CK_ULONG len, + CK_BYTE *iv, void *cb_data) +{ + struct aes_xts_param *param = cb_data; + int rc; + + int offset = AES_XTS_KM_XTSPARAM(param->keylen * 8); + memcpy(param->param_km + offset, iv, AES_BLOCK_SIZE); + + rc = s390_km(param->fc, param->param_km, out, in, len); + if (rc < 0) { + TRACE_ERROR("s390_km function failed\n"); + return CKR_FUNCTION_FAILED; + } + + memcpy(iv, param->param_km + offset, AES_BLOCK_SIZE); + return CKR_OK; +} + +/** + * Performs an AES-XTS operation via CPACF using a protected key. + */ +CK_RV pkey_aes_xts(OBJECT *key_obj, CK_BYTE *tweak, + CK_BYTE *in_data, CK_ULONG in_data_len, CK_BYTE *out_data, + CK_ULONG_PTR p_output_data_len, CK_BYTE encrypt, + CK_BBOOL initial, CK_BBOOL final, CK_BYTE *iv) +{ + CK_RV ret = CKR_OK; + CK_ATTRIBUTE *pkey_attr = NULL; + struct aes_xts_param param = {0}; + CK_ULONG keylen = 0; + unsigned long fc; + + /* Check parms */ + if (in_data_len == 0) { + ret = CKR_OK; + return CKR_OK; + } + + /* Handle implicit length_only parm (not passed down) */ + if (out_data == NULL) { + *p_output_data_len = in_data_len; + return CKR_OK; + } + + if (*p_output_data_len < in_data_len) { + TRACE_ERROR("Output buffer too small.\n"); + return CKR_BUFFER_TOO_SMALL; + } + + /* Get protected key from key object */ + if (template_attribute_get_non_empty(key_obj->template, CKA_IBM_OPAQUE_PKEY, + &pkey_attr) != CKR_OK) { + TRACE_ERROR("Could not find CKA_IBM_OPAQUE_PKEY in key's template.\n"); + return CKR_FUNCTION_FAILED; + } + + /* Determine clear key length */ + if (template_attribute_get_ulong(key_obj->template, CKA_VALUE_LEN, + &keylen) != CKR_OK) { + TRACE_ERROR("Cannot determine clear key len.\n"); + return CKR_FUNCTION_FAILED; + } + + /* Set function code */ + fc = get_xts_function_code(keylen, encrypt); + if (fc == 0) { + TRACE_ERROR("Could not determine CPACF fc for given keylen %ld\n", + keylen); + return CKR_FUNCTION_FAILED; + } + keylen = keylen / 2; + + memcpy(param.param_km, pkey_attr->pValue, pkey_attr->ulValueLen / 2); + memcpy(param.param_pcc, (CK_BYTE *)pkey_attr->pValue + pkey_attr->ulValueLen / 2, + pkey_attr->ulValueLen / 2); + param.fc = fc; + param.keylen = keylen; + + ret = aes_xts_cipher(in_data, in_data_len, out_data, p_output_data_len, + tweak, encrypt, initial, final, iv, + pkey_aes_xts_iv_from_tweak, + pkey_aes_xts_cipher_blocks, + ¶m); + + return ret; +} /** * Determine the CPACF curve type from given template. diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/pkey_utils.h opencryptoki-3.20.0+dfsg/usr/lib/common/pkey_utils.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/pkey_utils.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/pkey_utils.h 2023-02-13 09:22:42.000000000 +0100 @@ -33,6 +33,12 @@ #define ENCRYPTED_AES_256 0x1c /** + * function codes for the KM/KMC/KMAC instruction. + */ +#define ENCRYPTED_AES_XTS_128 0x3a +#define ENCRYPTED_AES_XTS_256 0x3c + +/** * function codes for the KDSA instruction. */ #define KDSA_ECDSA_VERIFY_P256 0x01 @@ -97,6 +103,11 @@ CK_RV pkey_aes_cmac(OBJECT *key_obj, CK_BYTE *message, CK_ULONG message_len, CK_BYTE *cmac, CK_BYTE *iv); +CK_RV pkey_aes_xts(OBJECT *key_obj, CK_BYTE *tweak, + CK_BYTE *in_data, CK_ULONG in_data_len, CK_BYTE *out_data, + CK_ULONG_PTR p_output_data_len, CK_BYTE encrypt, CK_BBOOL initial, + CK_BBOOL final, CK_BYTE *iv); + CK_RV pkey_ec_sign(OBJECT *privkey, CK_BYTE *hash, CK_ULONG hashlen, CK_BYTE *sig, CK_ULONG *sig_len, void (*rng_cb)(unsigned char *, size_t)); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/pqc_defs.h opencryptoki-3.20.0+dfsg/usr/lib/common/pqc_defs.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/pqc_defs.h 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/pqc_defs.h 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,43 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#ifndef _PQC_DEFS +#define _PQC_DEFS + +#include + +#include "pqc_oids.h" + +extern const CK_BYTE dilithium_r2_65[]; +extern const CK_BYTE dilithium_r2_87[]; +extern const CK_BYTE dilithium_r3_44[]; +extern const CK_BYTE dilithium_r3_56[]; +extern const CK_BYTE dilithium_r3_87[]; + +extern const CK_BYTE kyber_r2_768[]; +extern const CK_BYTE kyber_r2_1024[]; + +struct pqc_oid { + const CK_BYTE *oid; + CK_ULONG oid_len; + CK_ULONG keyform; + CK_ULONG policy_size; + CK_ULONG policy_siglen; +}; + +extern const struct pqc_oid dilithium_oids[]; +extern const struct pqc_oid kyber_oids[]; + +const struct pqc_oid *find_pqc_by_keyform(const struct pqc_oid *pqcs, + CK_ULONG keyform); +const struct pqc_oid *find_pqc_by_oid(const struct pqc_oid *pqcs, + CK_BYTE *oid, CK_ULONG oid_len); + +#endif diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/pqc_supported.c opencryptoki-3.20.0+dfsg/usr/lib/common/pqc_supported.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/pqc_supported.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/pqc_supported.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,80 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#include +#include "pkcs11types.h" +#include "pqc_defs.h" + +const CK_BYTE dilithium_r2_65[] = OCK_DILITHIUM_R2_65; +const CK_BYTE dilithium_r2_87[] = OCK_DILITHIUM_R2_87; +const CK_BYTE dilithium_r3_44[] = OCK_DILITHIUM_R3_44; +const CK_BYTE dilithium_r3_65[] = OCK_DILITHIUM_R3_65; +const CK_BYTE dilithium_r3_87[] = OCK_DILITHIUM_R3_87; + +const struct pqc_oid dilithium_oids[] = { + { .oid = dilithium_r2_65, .oid_len = sizeof(dilithium_r2_65), + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_65, + .policy_size = 256, .policy_siglen = 3366 }, + { .oid = dilithium_r2_87, .oid_len = sizeof(dilithium_r2_87), + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_87, + .policy_size = 256, .policy_siglen = 4668 }, + { .oid = dilithium_r3_44, .oid_len = sizeof(dilithium_r3_44), + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_44, + .policy_size = 256, .policy_siglen = 2420 }, + { .oid = dilithium_r3_65, .oid_len = sizeof(dilithium_r3_65), + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_65, + .policy_size = 256, .policy_siglen = 3293 }, + { .oid = dilithium_r3_87, .oid_len = sizeof(dilithium_r3_87), + .keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_87, + .policy_size = 256, .policy_siglen = 4595 }, + { .oid = NULL, .oid_len = 0, .keyform = 0, + .policy_size = 0, .policy_siglen = 0 } +}; + +const CK_BYTE kyber_r2_768[] = OCK_KYBER_R2_768; +const CK_BYTE kyber_r2_1024[] = OCK_KYBER_R2_1024; + +const struct pqc_oid kyber_oids[] = { + { .oid = kyber_r2_768, .oid_len = sizeof(kyber_r2_768), + .keyform = CK_IBM_KYBER_KEYFORM_ROUND2_768, + .policy_size = 256, .policy_siglen = 0 }, + { .oid = kyber_r2_1024, .oid_len = sizeof(kyber_r2_1024), + .keyform = CK_IBM_KYBER_KEYFORM_ROUND2_1024, + .policy_size = 256, .policy_siglen = 0 }, + { .oid = NULL, .oid_len = 0, .keyform = 0, + .policy_size = 0, .policy_siglen = 0 } +}; + +const struct pqc_oid *find_pqc_by_keyform(const struct pqc_oid *pqcs, + CK_ULONG keyform) +{ + CK_ULONG i; + + for (i = 0; pqcs[i].oid != NULL; i++) { + if (pqcs[i].keyform == keyform) + return &pqcs[i]; + } + + return NULL; +} + +const struct pqc_oid *find_pqc_by_oid(const struct pqc_oid *pqcs, + CK_BYTE *oid, CK_ULONG oid_len) +{ + CK_ULONG i; + + for (i = 0; pqcs[i].oid != NULL; i++) { + if (pqcs[i].oid_len == oid_len && + memcmp(pqcs[i].oid, oid, oid_len) == 0) + return &pqcs[i]; + } + + return NULL; +} diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/sess_mgr.c opencryptoki-3.20.0+dfsg/usr/lib/common/sess_mgr.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/sess_mgr.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/sess_mgr.c 2023-02-13 09:22:42.000000000 +0100 @@ -538,12 +538,14 @@ // // -CK_RV session_mgr_get_op_state(SESSION *sess, +CK_RV session_mgr_get_op_state(STDLL_TokData_t *tokdata, SESSION *sess, CK_BBOOL length_only, CK_BYTE *data, CK_ULONG *data_len) { OP_STATE_DATA *op_data = NULL; - CK_ULONG op_data_len = 0; + CK_ULONG max_data_len = *data_len; + CK_ULONG op_data_len; + CK_ULONG all_data_len = 0; CK_ULONG offset, active_ops; if (!sess) { @@ -566,22 +568,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(ENCR_DECR_CONTEXT) + sess->encr_ctx.context_len + sess->encr_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_ENCR; @@ -605,6 +614,9 @@ sess->encr_ctx.mech.pParameter, sess->encr_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } @@ -614,22 +626,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(ENCR_DECR_CONTEXT) + sess->decr_ctx.context_len + sess->decr_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_DECR; @@ -653,6 +672,9 @@ sess->decr_ctx.mech.pParameter, sess->decr_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } @@ -662,22 +684,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(DIGEST_CONTEXT) + sess->digest_ctx.context_len + sess->digest_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_DIGEST; @@ -701,6 +730,9 @@ sess->digest_ctx.mech.pParameter, sess->digest_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } @@ -710,22 +742,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(SIGN_VERIFY_CONTEXT) + sess->sign_ctx.context_len + sess->sign_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_SIGN; @@ -749,6 +788,9 @@ sess->sign_ctx.mech.pParameter, sess->sign_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } @@ -758,22 +800,29 @@ return CKR_STATE_UNSAVEABLE; } active_ops++; - if (op_data != NULL) { - TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); - return CKR_STATE_UNSAVEABLE; - } op_data_len = sizeof(OP_STATE_DATA) + sizeof(SIGN_VERIFY_CONTEXT) + sess->verify_ctx.context_len + sess->verify_ctx.mech.ulParameterLen; + all_data_len += op_data_len; if (length_only == FALSE) { op_data = (OP_STATE_DATA *) data; - if (*data_len < op_data_len) { + if (max_data_len < op_data_len) { TRACE_ERROR("%s\n", ock_err(ERR_BUFFER_TOO_SMALL)); return CKR_BUFFER_TOO_SMALL; } + memset(op_data, 0, sizeof(*op_data)); +#ifdef PACKAGE_VERSION + strncpy((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)); +#endif + memcpy(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)); + memcpy(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)); op_data->data_len = op_data_len - sizeof(OP_STATE_DATA); op_data->session_state = sess->session_info.state; op_data->active_operation = STATE_VERIFY; @@ -797,15 +846,18 @@ sess->verify_ctx.mech.pParameter, sess->verify_ctx.mech.ulParameterLen); } + + max_data_len -= op_data_len; + data += op_data_len; } } - if (!active_ops) { + if (active_ops == 0) { TRACE_ERROR("%s\n", ock_err(ERR_STATE_UNSAVEABLE)); return CKR_OPERATION_NOT_INITIALIZED; } - *data_len = op_data_len; + *data_len = all_data_len; return CKR_OK; } @@ -817,6 +869,8 @@ CK_OBJECT_HANDLE auth_key, CK_BYTE *data, CK_ULONG data_len) { + CK_BYTE *cur_data; + CK_ULONG cur_data_len; OP_STATE_DATA *op_data = NULL; CK_BYTE *mech_param = NULL; CK_BYTE *context = NULL; @@ -824,226 +878,369 @@ CK_BYTE *ptr2 = NULL; CK_BYTE *ptr3 = NULL; CK_ULONG len; + CK_ULONG encr_key_needed = 0; + CK_ULONG auth_key_needed = 0; if (!sess || !data) { TRACE_ERROR("%s received bad argument(s)\n", __func__); return CKR_FUNCTION_FAILED; } - op_data = (OP_STATE_DATA *) data; - if (data_len < op_data->data_len + sizeof(OP_STATE_DATA)) { + /* + * Validate the new state information. Don't touch the session + * until the new state is valid. + */ + cur_data = data; + cur_data_len = data_len; + while (cur_data_len >= sizeof(OP_STATE_DATA)) { + op_data = (OP_STATE_DATA *)cur_data; + + if (cur_data_len < op_data->data_len + sizeof(OP_STATE_DATA)) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + /* + * Make sure the session states are compatible: same OCK version, + * same token model, same session state. + */ +#ifdef PACKAGE_VERSION + if (strncmp((char *)op_data->library_version, PACKAGE_VERSION, + sizeof(op_data->library_version)) != 0) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } +#endif + if (memcmp(op_data->manufacturerID, + tokdata->nv_token_data->token_info.manufacturerID, + sizeof(op_data->manufacturerID)) != 0 || + memcmp(op_data->model, tokdata->nv_token_data->token_info.model, + sizeof(op_data->model)) != 0) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + if (sess->session_info.state != op_data->session_state) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + switch (op_data->active_operation) { + case STATE_ENCR: + case STATE_DECR: + { + ENCR_DECR_CONTEXT *ctx = + (ENCR_DECR_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(ENCR_DECR_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + encr_key_needed++; + } + break; + + case STATE_SIGN: + case STATE_VERIFY: + { + SIGN_VERIFY_CONTEXT *ctx = + (SIGN_VERIFY_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(SIGN_VERIFY_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + auth_key_needed++; + } + break; + + case STATE_DIGEST: + { + DIGEST_CONTEXT *ctx = + (DIGEST_CONTEXT *) (cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(DIGEST_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + } + break; + default: + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + /* move on to next operation */ + cur_data_len -= (op_data->data_len + sizeof(OP_STATE_DATA)); + cur_data += (op_data->data_len + sizeof(OP_STATE_DATA)); + } + /* nothing must be left over */ + if (cur_data_len > 0) { TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); return CKR_SAVED_STATE_INVALID; } - // make sure the session states are compatible - // - if (sess->session_info.state != op_data->session_state) { - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; + if (encr_key_needed > 0 && encr_key == CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); + return CKR_KEY_NEEDED; } - // validate the new state information. don't touch the session - // until the new state is valid. - // - switch (op_data->active_operation) { - case STATE_ENCR: - case STATE_DECR: - { - ENCR_DECR_CONTEXT *ctx = - (ENCR_DECR_CONTEXT *) (data + sizeof(OP_STATE_DATA)); - - len = - sizeof(ENCR_DECR_CONTEXT) + ctx->context_len + - ctx->mech.ulParameterLen; - if (len != op_data->data_len) { - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; - } - if (auth_key != CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); - return CKR_KEY_NOT_NEEDED; - } - if (encr_key == CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); - return CKR_KEY_NEEDED; - } - ptr1 = (CK_BYTE *) ctx; - ptr2 = ptr1 + sizeof(ENCR_DECR_CONTEXT); - ptr3 = ptr2 + ctx->context_len; - - if (ctx->context_len) { - context = (CK_BYTE *) malloc(ctx->context_len); - if (!context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(context, ptr2, ctx->context_len); - } - - if (ctx->mech.ulParameterLen) { - mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); - if (!mech_param) { - if (context) - free(context); - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); - } - } - break; - case STATE_SIGN: - case STATE_VERIFY: - { - SIGN_VERIFY_CONTEXT *ctx = - (SIGN_VERIFY_CONTEXT *) (data + sizeof(OP_STATE_DATA)); - - len = - sizeof(SIGN_VERIFY_CONTEXT) + ctx->context_len + - ctx->mech.ulParameterLen; - if (len != op_data->data_len) { - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; - } - if (auth_key == CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); - return CKR_KEY_NEEDED; - } - if (encr_key != CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); - return CKR_KEY_NOT_NEEDED; - } - ptr1 = (CK_BYTE *) ctx; - ptr2 = ptr1 + sizeof(SIGN_VERIFY_CONTEXT); - ptr3 = ptr2 + ctx->context_len; - - if (ctx->context_len) { - context = (CK_BYTE *) malloc(ctx->context_len); - if (!context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(context, ptr2, ctx->context_len); - } - - if (ctx->mech.ulParameterLen) { - mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); - if (!mech_param) { - if (context) - free(context); - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); - } - } - break; - case STATE_DIGEST: - { - DIGEST_CONTEXT *ctx = - (DIGEST_CONTEXT *) (data + sizeof(OP_STATE_DATA)); - - len = - sizeof(DIGEST_CONTEXT) + ctx->context_len + - ctx->mech.ulParameterLen; - if (len != op_data->data_len) { - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; - } - if (auth_key != CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); - return CKR_KEY_NOT_NEEDED; - } - if (encr_key != CK_INVALID_HANDLE) { - TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); - return CKR_KEY_NOT_NEEDED; - } - ptr1 = (CK_BYTE *) ctx; - ptr2 = ptr1 + sizeof(DIGEST_CONTEXT); - ptr3 = ptr2 + ctx->context_len; - - if (ctx->context_len) { - context = (CK_BYTE *) malloc(ctx->context_len); - if (!context) { - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; - } - memcpy(context, ptr2, ctx->context_len); - } - - if (ctx->mech.ulParameterLen) { - mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); - if (!mech_param) { - if (context) - free(context); - TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); - return CKR_HOST_MEMORY; + if (encr_key_needed == 0 && encr_key != CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); + return CKR_KEY_NOT_NEEDED; + } + if (auth_key_needed > 0 && auth_key == CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); + return CKR_KEY_NEEDED; + } + if (auth_key_needed == 0 && auth_key != CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NOT_NEEDED)); + return CKR_KEY_NOT_NEEDED; + } + + /* State information looks okay. Cleanup the current session state, first */ + if (sess->encr_ctx.active) + encr_mgr_cleanup(tokdata, sess, &sess->encr_ctx); + if (sess->decr_ctx.active) + decr_mgr_cleanup(tokdata, sess, &sess->decr_ctx); + if (sess->digest_ctx.active) + digest_mgr_cleanup(tokdata, sess, &sess->digest_ctx); + if (sess->sign_ctx.active) + sign_mgr_cleanup(tokdata, sess, &sess->sign_ctx); + if (sess->verify_ctx.active) + verify_mgr_cleanup(tokdata, sess, &sess->verify_ctx); + + /* Now process the saved operation states */ + cur_data = data; + cur_data_len = data_len; + while (cur_data_len >= sizeof(OP_STATE_DATA)) { + op_data = (OP_STATE_DATA *)cur_data; + + if (cur_data_len < op_data->data_len + sizeof(OP_STATE_DATA)) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + + switch (op_data->active_operation) { + case STATE_ENCR: + case STATE_DECR: + { + ENCR_DECR_CONTEXT *ctx = + (ENCR_DECR_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(ENCR_DECR_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + if (encr_key == CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); + return CKR_KEY_NEEDED; + } + ptr1 = (CK_BYTE *) ctx; + ptr2 = ptr1 + sizeof(ENCR_DECR_CONTEXT); + ptr3 = ptr2 + ctx->context_len; + + if (ctx->context_len) { + context = (CK_BYTE *) malloc(ctx->context_len); + if (!context) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(context, ptr2, ctx->context_len); + } + + if (ctx->mech.ulParameterLen) { + mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); + if (!mech_param) { + if (context) + free(context); + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); + } + } + break; + + case STATE_SIGN: + case STATE_VERIFY: + { + SIGN_VERIFY_CONTEXT *ctx = + (SIGN_VERIFY_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(SIGN_VERIFY_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + if (auth_key == CK_INVALID_HANDLE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_NEEDED)); + return CKR_KEY_NEEDED; + } + ptr1 = (CK_BYTE *) ctx; + ptr2 = ptr1 + sizeof(SIGN_VERIFY_CONTEXT); + ptr3 = ptr2 + ctx->context_len; + + if (ctx->context_len) { + context = (CK_BYTE *) malloc(ctx->context_len); + if (!context) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(context, ptr2, ctx->context_len); + } + + if (ctx->mech.ulParameterLen) { + mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); + if (!mech_param) { + if (context) + free(context); + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); + } + } + break; + + case STATE_DIGEST: + { + DIGEST_CONTEXT *ctx = + (DIGEST_CONTEXT *)(cur_data + sizeof(OP_STATE_DATA)); + + len = sizeof(DIGEST_CONTEXT) + ctx->context_len + + ctx->mech.ulParameterLen; + if (len != op_data->data_len) { + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; + } + ptr1 = (CK_BYTE *) ctx; + ptr2 = ptr1 + sizeof(DIGEST_CONTEXT); + ptr3 = ptr2 + ctx->context_len; + + if (ctx->context_len) { + context = (CK_BYTE *) malloc(ctx->context_len); + if (!context) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(context, ptr2, ctx->context_len); + } + + if (ctx->mech.ulParameterLen) { + mech_param = (CK_BYTE *) malloc(ctx->mech.ulParameterLen); + if (!mech_param) { + if (context) + free(context); + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + return CKR_HOST_MEMORY; + } + memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); } - memcpy(mech_param, ptr3, ctx->mech.ulParameterLen); } + break; + default: + TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); + return CKR_SAVED_STATE_INVALID; } - break; - default: - TRACE_ERROR("%s\n", ock_err(ERR_SAVED_STATE_INVALID)); - return CKR_SAVED_STATE_INVALID; + + /* copy the new state information */ + switch (op_data->active_operation) { + case STATE_ENCR: + memcpy(&sess->encr_ctx, ptr1, sizeof(ENCR_DECR_CONTEXT)); + + sess->encr_ctx.key = encr_key; + sess->encr_ctx.context = context; + sess->encr_ctx.mech.pParameter = mech_param; + break; + + case STATE_DECR: + memcpy(&sess->decr_ctx, ptr1, sizeof(ENCR_DECR_CONTEXT)); + + sess->decr_ctx.key = encr_key; + sess->decr_ctx.context = context; + sess->decr_ctx.mech.pParameter = mech_param; + break; + + case STATE_SIGN: + memcpy(&sess->sign_ctx, ptr1, sizeof(SIGN_VERIFY_CONTEXT)); + + sess->sign_ctx.key = auth_key; + sess->sign_ctx.context = context; + sess->sign_ctx.mech.pParameter = mech_param; + break; + + case STATE_VERIFY: + memcpy(&sess->verify_ctx, ptr1, sizeof(SIGN_VERIFY_CONTEXT)); + + sess->verify_ctx.key = auth_key; + sess->verify_ctx.context = context; + sess->verify_ctx.mech.pParameter = mech_param; + break; + + case STATE_DIGEST: + memcpy(&sess->digest_ctx, ptr1, sizeof(DIGEST_CONTEXT)); + + sess->digest_ctx.context = context; + sess->digest_ctx.mech.pParameter = mech_param; + break; + } + + context = NULL; + mech_param = NULL; + + /* move on to next operation */ + cur_data_len -= (op_data->data_len + sizeof(OP_STATE_DATA)); + cur_data += (op_data->data_len + sizeof(OP_STATE_DATA)); } + return CKR_OK; +} - // state information looks okay. cleanup the current session state, first - // - if (sess->encr_ctx.active) +CK_RV session_mgr_cancel(STDLL_TokData_t *tokdata, SESSION *sess, + CK_FLAGS flags) +{ + if ((flags & CKF_ENCRYPT) && sess->encr_ctx.active) encr_mgr_cleanup(tokdata, sess, &sess->encr_ctx); - if (sess->decr_ctx.active) + if ((flags & CKF_DECRYPT) && sess->decr_ctx.active) decr_mgr_cleanup(tokdata, sess, &sess->decr_ctx); - if (sess->digest_ctx.active) + if ((flags & CKF_DIGEST) && sess->digest_ctx.active) digest_mgr_cleanup(tokdata, sess, &sess->digest_ctx); - if (sess->sign_ctx.active) + if ((flags & CKF_SIGN) && sess->sign_ctx.active && + !sess->sign_ctx.recover) sign_mgr_cleanup(tokdata, sess, &sess->sign_ctx); - if (sess->verify_ctx.active) + if ((flags & CKF_SIGN_RECOVER) && sess->sign_ctx.active && + sess->sign_ctx.recover) + sign_mgr_cleanup(tokdata, sess, &sess->sign_ctx); + + if ((flags & CKF_VERIFY) && sess->verify_ctx.active && + !sess->verify_ctx.recover) verify_mgr_cleanup(tokdata, sess, &sess->verify_ctx); + if ((flags & CKF_VERIFY_RECOVER) && sess->verify_ctx.active && + sess->verify_ctx.recover) + verify_mgr_cleanup(tokdata, sess, &sess->verify_ctx); - // copy the new state information - // - switch (op_data->active_operation) { - case STATE_ENCR: - memcpy(&sess->encr_ctx, ptr1, sizeof(ENCR_DECR_CONTEXT)); - - sess->encr_ctx.key = encr_key; - sess->encr_ctx.context = context; - sess->encr_ctx.mech.pParameter = mech_param; - break; - case STATE_DECR: - memcpy(&sess->decr_ctx, ptr1, sizeof(ENCR_DECR_CONTEXT)); - - sess->decr_ctx.key = encr_key; - sess->decr_ctx.context = context; - sess->decr_ctx.mech.pParameter = mech_param; - break; - case STATE_SIGN: - memcpy(&sess->sign_ctx, ptr1, sizeof(SIGN_VERIFY_CONTEXT)); - - sess->sign_ctx.key = auth_key; - sess->sign_ctx.context = context; - sess->sign_ctx.mech.pParameter = mech_param; - break; - case STATE_VERIFY: - memcpy(&sess->verify_ctx, ptr1, sizeof(SIGN_VERIFY_CONTEXT)); - - sess->verify_ctx.key = auth_key; - sess->verify_ctx.context = context; - sess->verify_ctx.mech.pParameter = mech_param; - break; - case STATE_DIGEST: - memcpy(&sess->digest_ctx, ptr1, sizeof(DIGEST_CONTEXT)); - - sess->digest_ctx.context = context; - sess->digest_ctx.mech.pParameter = mech_param; - break; + if ((flags & CKF_FIND_OBJECTS) && sess->find_active) { + if (sess->find_list) + free(sess->find_list); + sess->find_list = NULL; + sess->find_len = 0; + sess->find_idx = 0; + sess->find_active = FALSE; } return CKR_OK; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/template.c opencryptoki-3.20.0+dfsg/usr/lib/common/template.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/template.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/template.c 2023-02-13 09:22:42.000000000 +0100 @@ -162,10 +162,10 @@ return ecdsa_publ_set_default_attributes(tmpl, mode); case CKK_DH: return dh_publ_set_default_attributes(tmpl, mode); - case CKK_KEA: - return kea_publ_set_default_attributes(tmpl, mode); case CKK_IBM_PQC_DILITHIUM: return ibm_dilithium_publ_set_default_attributes(tmpl, mode); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_publ_set_default_attributes(tmpl, mode); default: TRACE_ERROR("%s: %lx\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID), subclass); @@ -181,10 +181,10 @@ return ecdsa_priv_set_default_attributes(tmpl, mode); case CKK_DH: return dh_priv_set_default_attributes(tmpl, mode); - case CKK_KEA: - return kea_priv_set_default_attributes(tmpl, mode); case CKK_IBM_PQC_DILITHIUM: return ibm_dilithium_priv_set_default_attributes(tmpl, mode); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_priv_set_default_attributes(tmpl, mode); default: TRACE_ERROR("%s: %lx\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID), subclass); @@ -194,38 +194,16 @@ switch (subclass) { case CKK_GENERIC_SECRET: return generic_secret_set_default_attributes(tmpl, mode); - case CKK_RC2: - return rc2_set_default_attributes(tmpl, mode); - case CKK_RC4: - return rc4_set_default_attributes(tmpl, mode); - case CKK_RC5: - return rc5_set_default_attributes(tmpl, mode); case CKK_DES: return des_set_default_attributes(tmpl, mode); case CKK_DES2: return des2_set_default_attributes(tmpl, mode); case CKK_DES3: return des3_set_default_attributes(tmpl, mode); - case CKK_CAST: - return cast_set_default_attributes(tmpl, mode); - case CKK_CAST3: - return cast3_set_default_attributes(tmpl, mode); - case CKK_CAST5: - return cast5_set_default_attributes(tmpl, mode); - case CKK_IDEA: - return idea_set_default_attributes(tmpl, mode); -#if !(NOCDMF) - case CKK_CDMF: - return cdmf_set_default_attributes(tmpl, mode); -#endif - case CKK_SKIPJACK: - return skipjack_set_default_attributes(tmpl, mode); - case CKK_BATON: - return baton_set_default_attributes(tmpl, mode); - case CKK_JUNIPER: - return juniper_set_default_attributes(tmpl, mode); case CKK_AES: - return aes_set_default_attributes(tmpl, basetmpl, mode); + return aes_set_default_attributes(tmpl, basetmpl, mode, FALSE); + case CKK_AES_XTS: + return aes_set_default_attributes(tmpl, basetmpl, mode, TRUE); default: TRACE_ERROR("%s: %lx\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID), subclass); @@ -435,10 +413,10 @@ return ecdsa_publ_check_required_attributes(tmpl, mode); case CKK_DH: return dh_publ_check_required_attributes(tmpl, mode); - case CKK_KEA: - return kea_publ_check_required_attributes(tmpl, mode); case CKK_IBM_PQC_DILITHIUM: return ibm_dilithium_publ_check_required_attributes(tmpl, mode); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_publ_check_required_attributes(tmpl, mode); default: TRACE_ERROR("%s: %lx\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID), subclass); @@ -454,10 +432,10 @@ return ecdsa_priv_check_required_attributes(tmpl, mode); case CKK_DH: return dh_priv_check_required_attributes(tmpl, mode); - case CKK_KEA: - return kea_priv_check_required_attributes(tmpl, mode); case CKK_IBM_PQC_DILITHIUM: return ibm_dilithium_priv_check_required_attributes(tmpl, mode); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_priv_check_required_attributes(tmpl, mode); default: TRACE_ERROR("%s: %lx\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID), subclass); @@ -467,37 +445,14 @@ switch (subclass) { case CKK_GENERIC_SECRET: return generic_secret_check_required_attributes(tmpl, mode); - case CKK_RC2: - return rc2_check_required_attributes(tmpl, mode); - case CKK_RC4: - return rc4_check_required_attributes(tmpl, mode); - case CKK_RC5: - return rc5_check_required_attributes(tmpl, mode); case CKK_DES: return des_check_required_attributes(tmpl, mode); case CKK_DES2: return des2_check_required_attributes(tmpl, mode); case CKK_DES3: return des3_check_required_attributes(tmpl, mode); - case CKK_CAST: - return cast_check_required_attributes(tmpl, mode); - case CKK_CAST3: - return cast3_check_required_attributes(tmpl, mode); - case CKK_CAST5: - return cast5_check_required_attributes(tmpl, mode); - case CKK_IDEA: - return idea_check_required_attributes(tmpl, mode); -#if !(NOCDMF) - case CKK_CDMF: - return cdmf_check_required_attributes(tmpl, mode); -#endif - case CKK_SKIPJACK: - return skipjack_check_required_attributes(tmpl, mode); - case CKK_BATON: - return baton_check_required_attributes(tmpl, mode); - case CKK_JUNIPER: - return juniper_check_required_attributes(tmpl, mode); case CKK_AES: + case CKK_AES_XTS: return aes_check_required_attributes(tmpl, mode); default: TRACE_ERROR("%s: %lx\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID), @@ -1415,8 +1370,6 @@ case CKK_X9_42_DH: case CKK_DH: return dh_priv_check_exportability(type); - case CKK_KEA: - return kea_priv_check_exportability(type); default: TRACE_ERROR("%s: %lx\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID), subclass); @@ -1698,10 +1651,10 @@ return ecdsa_publ_validate_attribute(tokdata, tmpl, attr, mode); case CKK_DH: return dh_publ_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_KEA: - return kea_publ_validate_attribute(tokdata, tmpl, attr, mode); case CKK_IBM_PQC_DILITHIUM: return ibm_dilithium_publ_validate_attribute(tokdata, tmpl, attr, mode); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_publ_validate_attribute(tokdata, tmpl, attr, mode); default: TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); return CKR_ATTRIBUTE_VALUE_INVALID; // unknown key type @@ -1716,10 +1669,10 @@ return ecdsa_priv_validate_attribute(tokdata, tmpl, attr, mode); case CKK_DH: return dh_priv_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_KEA: - return kea_priv_validate_attribute(tokdata, tmpl, attr, mode); case CKK_IBM_PQC_DILITHIUM: return ibm_dilithium_priv_validate_attribute(tokdata, tmpl, attr, mode); + case CKK_IBM_PQC_KYBER: + return ibm_kyber_priv_validate_attribute(tokdata, tmpl, attr, mode); default: TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); return CKR_ATTRIBUTE_VALUE_INVALID; // unknown key type @@ -1728,38 +1681,16 @@ switch (subclass) { case CKK_GENERIC_SECRET: return generic_secret_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_RC2: - return rc2_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_RC4: - return rc4_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_RC5: - return rc5_validate_attribute(tokdata, tmpl, attr, mode); case CKK_DES: return des_validate_attribute(tokdata, tmpl, attr, mode); case CKK_DES2: return des2_validate_attribute(tokdata, tmpl, attr, mode); case CKK_DES3: return des3_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_CAST: - return cast_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_CAST3: - return cast3_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_CAST5: - return cast5_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_IDEA: - return idea_validate_attribute(tokdata, tmpl, attr, mode); -#if !(NOCDMF) - case CKK_CDMF: - return cdmf_validate_attribute(tokdata, tmpl, attr, mode); -#endif - case CKK_SKIPJACK: - return skipjack_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_BATON: - return baton_validate_attribute(tokdata, tmpl, attr, mode); - case CKK_JUNIPER: - return juniper_validate_attribute(tokdata, tmpl, attr, mode); case CKK_AES: - return aes_validate_attribute(tokdata, tmpl, attr, mode); + return aes_validate_attribute(tokdata, tmpl, attr, mode, FALSE); + case CKK_AES_XTS: + return aes_validate_attribute(tokdata, tmpl, attr, mode, TRUE); default: TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_VALUE_INVALID)); return CKR_ATTRIBUTE_VALUE_INVALID; // unknown key type diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/tok_specific.h opencryptoki-3.20.0+dfsg/usr/lib/common/tok_specific.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/tok_specific.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/tok_specific.h 2023-02-13 09:22:42.000000000 +0100 @@ -232,10 +232,12 @@ CK_RV token_specific_generic_secret_key_gen(STDLL_TokData_t *, TEMPLATE *template); -#ifndef NOAES CK_RV token_specific_aes_key_gen(STDLL_TokData_t *, CK_BYTE **, CK_ULONG *, CK_ULONG, CK_BBOOL *); +CK_RV token_specific_aes_xts_key_gen(STDLL_TokData_t *, + CK_BYTE **, CK_ULONG *, CK_ULONG, CK_BBOOL *); + CK_RV token_specific_aes_ecb(STDLL_TokData_t *, CK_BYTE *, CK_ULONG, @@ -286,7 +288,9 @@ CK_BYTE *, CK_ULONG, OBJECT *, CK_BYTE *, CK_BBOOL, CK_BBOOL, CK_VOID_PTR *); -#endif +CK_RV token_specific_aes_xts(STDLL_TokData_t *tokdata, CK_BYTE *, CK_ULONG, + CK_BYTE *, CK_ULONG *, OBJECT *, CK_BYTE *, + CK_BBOOL, CK_BBOOL, CK_BBOOL, CK_BYTE*); CK_RV token_specific_dsa_generate_keypair(STDLL_TokData_t *, TEMPLATE *, TEMPLATE *); @@ -319,8 +323,8 @@ CK_MECHANISM *, OBJECT *, CK_BYTE *, CK_ULONG , CK_BYTE *, CK_ULONG *); -CK_RV token_specific_set_attribute_values(STDLL_TokData_t *, OBJECT *, - TEMPLATE *); +CK_RV token_specific_set_attribute_values(STDLL_TokData_t *, SESSION *, + OBJECT *, TEMPLATE *); CK_RV token_specific_set_attrs_for_new_object(STDLL_TokData_t *, CK_OBJECT_CLASS, CK_ULONG, diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/tok_spec_struct.h opencryptoki-3.20.0+dfsg/usr/lib/common/tok_spec_struct.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/tok_spec_struct.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/tok_spec_struct.h 2023-02-13 09:22:42.000000000 +0100 @@ -212,6 +212,9 @@ CK_RV(*t_aes_key_gen) (STDLL_TokData_t *, CK_BYTE **, CK_ULONG *, CK_ULONG, CK_BBOOL *); + CK_RV(*t_aes_xts_key_gen) (STDLL_TokData_t *, CK_BYTE **, CK_ULONG *, CK_ULONG, + CK_BBOOL *); + CK_RV(*t_aes_ecb) (STDLL_TokData_t *tokdata, CK_BYTE *, CK_ULONG, CK_BYTE *, CK_ULONG *, OBJECT *, CK_BYTE); @@ -249,6 +252,10 @@ CK_RV(*t_aes_cmac) (STDLL_TokData_t *, CK_BYTE *, CK_ULONG, OBJECT *, CK_BYTE *, CK_BBOOL, CK_BBOOL, CK_VOID_PTR *); + CK_RV(*t_aes_xts) (STDLL_TokData_t *tokdata, CK_BYTE *, CK_ULONG, + CK_BYTE *, CK_ULONG *, OBJECT *, CK_BYTE *, CK_BBOOL, + CK_BBOOL, CK_BBOOL, CK_BYTE*); + // Token Specific DSA functions CK_RV(*t_dsa_generate_keypair) (STDLL_TokData_t *, TEMPLATE *, TEMPLATE *); @@ -274,7 +281,8 @@ ENCR_DECR_CONTEXT *, CK_MECHANISM *, OBJECT *, CK_BYTE *, CK_ULONG , CK_BYTE *, CK_ULONG *); - CK_RV(*t_set_attribute_values) (STDLL_TokData_t *, OBJECT *, TEMPLATE *); + CK_RV(*t_set_attribute_values) (STDLL_TokData_t *, SESSION *, + OBJECT *, TEMPLATE *); CK_RV(*t_set_attrs_for_new_object) (STDLL_TokData_t *, CK_OBJECT_CLASS, CK_ULONG, TEMPLATE *); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/trace.h opencryptoki-3.20.0+dfsg/usr/lib/common/trace.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/trace.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/trace.h 2023-02-13 09:22:42.000000000 +0100 @@ -119,8 +119,8 @@ extern struct trace_handle_t trace; void set_trace(struct trace_handle_t t); -CK_RV trace_initialize(); -void trace_finalize(); +CK_RV trace_initialize(void); +void trace_finalize(void); void ock_traceit(trace_level_t level, const char *file, int line, const char *stdll_name, const char *fmt, ...) __attribute__ ((format(printf, 5, 6))); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/uri.c opencryptoki-3.20.0+dfsg/usr/lib/common/uri.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/uri.c 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/uri.c 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,270 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#include +#include + +#include +#include +#include +#include +#include + +#define buffer_get(u) (p11_buffer_t *)(u)->priv + +#define P11_URI_SEP_PROT ':' +#define P11_URI_SEP_ATTR ';' +#define P11_URI_SEP_QUERY '&' + +#define START_END(c, c_max) \ + (const CK_CHAR *)(c), \ + (const CK_CHAR *)((CK_CHAR *)c + p11_strlen(c, c_max)) + +#define FORMAT_STRING(sep, txt, s, buf) \ + do { \ + if (p11_strlen((s), sizeof(s))) { \ + p11_buffer_append_len(buf, sep, 1); \ + p11_buffer_append(buf, txt); \ + p11_url_encode(START_END((s), sizeof(s)), \ + P11_URI_P_UNRES, buf); \ + *sep = P11_URI_SEP_ATTR; \ + } \ + } while(0) + +#define FORMAT_ATTRIBUTE_STRING(sep, txt, a, t, buf) \ + do { \ + if (((a)[0].type == (t)) && \ + ((a)[0].pValue)) { \ + p11_buffer_append_len(buf, sep, 1); \ + p11_buffer_append(buf, txt); \ + p11_url_encode(START_END((a)[0].pValue, (a)[0].ulValueLen), \ + P11_URI_P_UNRES, buf); \ + *sep = P11_URI_SEP_ATTR; \ + } \ + } while(0) + +#define FORMAT_ATTRIBUTE_ALL(sep, txt, a, t, buf) \ + do { \ + if (((a)[0].type == (t)) && \ + ((a)[0].pValue)) { \ + p11_buffer_append_len(buf, sep, 1); \ + p11_buffer_append(buf, txt); \ + p11_encode(START_END((a)[0].pValue, \ + (a)[0].ulValueLen), \ + buf); \ + *sep = P11_URI_SEP_ATTR; \ + } \ + } while(0) + +#define FORMAT_ATTRIBUTE_CLASS(sep, txt, a, buf) \ + do { \ + if (((a)[0].type == CKA_CLASS) && \ + ((a)[0].pValue) && \ + (rfc7512_get_cko((a)[0].pValue))) { \ + p11_buffer_append_len(buf, sep, 1); \ + p11_buffer_append(buf, txt); \ + p11_buffer_append(buf, rfc7512_get_cko((a)[0].pValue)); \ + *sep = P11_URI_SEP_ATTR; \ + } \ + } while(0) + +#define FORMAT_VERSION(sep, txt, v, buf) \ + do { \ + if (((v).major != (CK_BYTE)-1) || \ + ((v).minor != (CK_BYTE)-1)) { \ + p11_buffer_append_len(buf, sep, 1); \ + p11_buffer_append_printf(buf, txt "%d.%d", \ + (v).major, (v).minor); \ + *sep = P11_URI_SEP_ATTR; \ + } \ + } while(0) + +#define FORMAT_ULONG(sep, txt, ul, buf) \ + do { \ + if ((ul) != (CK_ULONG)-1) { \ + p11_buffer_append_len(buf, sep, 1); \ + p11_buffer_append_printf(buf, txt "%lu", ul); \ + *sep = P11_URI_SEP_ATTR; \ + } \ + } while(0) + +static const char HEX_CHARS_LOWER[] = "0123456789abcdef"; + +static char *rfc7512_get_cko(CK_OBJECT_CLASS *class) +{ + switch (*class) { + case CKO_CERTIFICATE: + return "cert"; + case CKO_DATA: + return "data"; + case CKO_PRIVATE_KEY: + return "private"; + case CKO_PUBLIC_KEY: + return "public"; + case CKO_SECRET_KEY: + return "secret-key"; + default: + break; + } + return NULL; +} + +static void p11_encode(const unsigned char *start, + const unsigned char *end, + p11_buffer_t *buf) +{ + unsigned char hex[3]; + + if (end <= start) + return; + + while (start != end) { + /* encoding required */ + hex[0] = '%'; + hex[1] = HEX_CHARS_LOWER[(*start) >> 4]; + hex[2] = HEX_CHARS_LOWER[(*start) & 0x0F]; + + p11_buffer_append_len(buf, (const char *)hex, 3); + + ++start; + } +} + +static void p11_url_encode(const unsigned char *start, + const unsigned char *end, + const char *verbatim, + p11_buffer_t *buf) +{ + while (start != end) { + if (*start && strchr(verbatim, *start) != NULL) { + /* no encoding */ + p11_buffer_append_len(buf, (const char *)start, 1); + } else { + p11_encode(start, start + 1, buf); + } + + ++start; + } +} + +static void p11_uri_init(struct p11_uri *uri) +{ + uri->slot_id = (CK_ULONG) - 1; + uri->obj_id[0].type = CKA_ID; + uri->obj_label[0].type = CKA_LABEL; + uri->obj_class[0].type = CKA_CLASS; + + p11_buffer_reset(buffer_get(uri)); +} + +const char *p11_uri_format(struct p11_uri *uri) +{ + p11_buffer_t *buf; + char sep; + + if (!uri) + return NULL; + buf = buffer_get(uri); + + p11_buffer_reset(buf); + + p11_buffer_append(buf, "pkcs11"); + sep = P11_URI_SEP_PROT; + + /* CK_INFO */ + if (uri->info) { + FORMAT_STRING(&sep, "library-description=", + uri->info->libraryDescription, buf); + FORMAT_STRING(&sep, "library-manufacturer=", + uri->info->manufacturerID, buf); + FORMAT_VERSION(&sep, "library-version=", + uri->info->libraryVersion, buf); + } + + FORMAT_ULONG(&sep, "slot-id=", + uri->slot_id, buf); + + /* CK_SLOT_INFO */ + if (uri->slot_info) { + FORMAT_STRING(&sep, "slot-description=", + uri->slot_info->slotDescription, buf); + FORMAT_STRING(&sep, "slot-manufacturer=", + uri->slot_info->manufacturerID, buf); + } + + /* CK_TOKEN_INFO */ + if (uri->token_info) { + FORMAT_STRING(&sep, "manufacturer=", + uri->token_info->manufacturerID, buf); + FORMAT_STRING(&sep, "model=", + uri->token_info->model, buf); + FORMAT_STRING(&sep, "serial=", + uri->token_info->serialNumber, buf); + FORMAT_STRING(&sep, "token=", + uri->token_info->label, buf); + } + + /* OBJECT */ + FORMAT_ATTRIBUTE_ALL(&sep, "id=", uri->obj_id, CKA_ID, buf); + FORMAT_ATTRIBUTE_STRING(&sep, "object=", uri->obj_label, CKA_LABEL, buf); + FORMAT_ATTRIBUTE_CLASS(&sep, "type=", uri->obj_class, buf); + + /* append the protocol separator for empty URI */ + if (sep == P11_URI_SEP_PROT) + p11_buffer_append_len(buf, &sep, 1); + + return p11_buffer_char(buf); +} + +struct p11_uri *p11_uri_new(void) +{ + struct p11_uri *uri; + + if (!(uri = calloc(1, sizeof(struct p11_uri)))) + goto out; + + if (!(uri->priv = (void *) p11_buffer_new())) + goto err; + + p11_uri_init(uri); +out: + return uri; + +err: + free(uri); + return NULL_PTR; +} + +static void p11_uri_attribute_free(CK_ATTRIBUTE_PTR attr) +{ + if (attr->pValue) + free(attr->pValue); + attr->pValue = NULL; + attr->ulValueLen = 0; +} + +void p11_uri_attributes_free(struct p11_uri *uri) +{ + if (!uri) + return; + + p11_uri_attribute_free(&uri->obj_id[0]); + p11_uri_attribute_free(&uri->obj_label[0]); + p11_uri_attribute_free(&uri->obj_class[0]); +} + +void p11_uri_free(struct p11_uri *uri) +{ + if (!uri) + return; + + p11_buffer_free((p11_buffer_t *) uri->priv); + free(uri); +} diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/uri_enc.h opencryptoki-3.20.0+dfsg/usr/lib/common/uri_enc.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/uri_enc.h 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/uri_enc.h 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,32 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#ifndef __URI_ENC_H +#define __URI_ENC_H + +#define URL_UNRES \ + "abcdefghijklmnopqrstuvwxyz" \ + "ABCDEFGHIJKLMNOPQRSTUVWXYZ" \ + "0123456789_-." + +#define P11_URI_UNRES \ + ":[]@!$\'()*+,=" + +#define P11_URI_P_UNRES \ + URL_UNRES \ + P11_URI_UNRES \ + "&" + +#define P11_URI_Q_UNRES \ + URL_UNRES \ + P11_URI_UNRES \ + "/?|" + +#endif /* __URI_ENC_H */ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/uri.h opencryptoki-3.20.0+dfsg/usr/lib/common/uri.h --- opencryptoki-3.18.0+dfsg/usr/lib/common/uri.h 1970-01-01 01:00:00.000000000 +0100 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/uri.h 2023-02-13 09:22:42.000000000 +0100 @@ -0,0 +1,33 @@ +/* + * COPYRIGHT (c) International Business Machines Corp. 2022 + * + * This program is provided under the terms of the Common Public License, + * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this + * software constitutes recipient's acceptance of CPL-1.0 terms which can be + * found in the file LICENSE file or at + * https://opensource.org/licenses/cpl1.0.php + */ + +#ifndef __URI_H +#define __URI_H + +#include +#include + +struct p11_uri { + CK_INFO_PTR info; + CK_SLOT_ID slot_id; + CK_SLOT_INFO_PTR slot_info; + CK_TOKEN_INFO_PTR token_info; + CK_ATTRIBUTE obj_id[1]; + CK_ATTRIBUTE obj_label[1]; + CK_ATTRIBUTE obj_class[1]; + void *priv; +}; + +const char *p11_uri_format(struct p11_uri *uri); +struct p11_uri *p11_uri_new(void); +void p11_uri_attributes_free(struct p11_uri *uri); +void p11_uri_free(struct p11_uri *uri); + +#endif /* __URI_H */ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/utility.c opencryptoki-3.20.0+dfsg/usr/lib/common/utility.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/utility.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/utility.c 2023-02-13 09:22:42.000000000 +0100 @@ -298,15 +298,7 @@ // token_info->flags = CKF_RNG | CKF_LOGIN_REQUIRED | CKF_CLOCK_ON_TOKEN | - CKF_SO_PIN_TO_BE_CHANGED; - // XXX New in v2.11 - KEY - - if (memcmp(nv_token_data->user_pin_sha, "00000000000000000000", - SHA1_HASH_SIZE) != 0) - token_info->flags |= CKF_USER_PIN_INITIALIZED; - else - token_info->flags |= CKF_USER_PIN_TO_BE_CHANGED; - // XXX New in v2.11 - KEY + CKF_SO_PIN_TO_BE_CHANGED | CKF_USER_PIN_TO_BE_CHANGED; // For the release, we made these // values as CK_UNAVAILABLE_INFORMATION or CK_EFFECTIVELY_INFINITE @@ -593,7 +585,7 @@ rc = XProcLock(tokdata); if (rc != CKR_OK) - goto err; + return rc; /* * Attach to an existing shared memory region or create it if it doesn't @@ -625,7 +617,7 @@ rc = XProcLock(tokdata); if (rc != CKR_OK) - goto err; + return rc; if (sm_close((void *) tokdata->global_shm, 0, ignore_ref_count)) { TRACE_DEVEL("sm_close failed.\n"); @@ -871,6 +863,6 @@ pInfo->ulMaxSessionCount = CK_EFFECTIVELY_INFINITE; /* pInfo->ulSessionCount is set at the API level */ pInfo->ulMaxRwSessionCount = CK_EFFECTIVELY_INFINITE; - pInfo->ulRwSessionCount = CK_UNAVAILABLE_INFORMATION; + /* pInfo->ulRwSessionCount is set at the API level */ } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/utility_common.c opencryptoki-3.20.0+dfsg/usr/lib/common/utility_common.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/utility_common.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/utility_common.c 2023-02-13 09:22:42.000000000 +0100 @@ -91,11 +91,13 @@ CK_RV get_hmac_digest(CK_ULONG mech, CK_ULONG *digest_mech, CK_BBOOL *general) { switch (mech) { +#if !(NOMD2 ) case CKM_MD2_HMAC: case CKM_MD2_HMAC_GENERAL: *digest_mech = CKM_MD2; *general = (mech == CKM_MD2_HMAC_GENERAL); break; +#endif case CKM_MD5_HMAC: case CKM_MD5_HMAC_GENERAL: *digest_mech = CKM_MD5; @@ -167,18 +169,23 @@ { switch (kdf) { case CKD_SHA1_KDF: + case CKD_IBM_HYBRID_SHA1_KDF: *mech = CKM_SHA_1; break; case CKD_SHA224_KDF: + case CKD_IBM_HYBRID_SHA224_KDF: *mech = CKM_SHA224; break; case CKD_SHA256_KDF: + case CKD_IBM_HYBRID_SHA256_KDF: *mech = CKM_SHA256; break; case CKD_SHA384_KDF: + case CKD_IBM_HYBRID_SHA384_KDF: *mech = CKM_SHA384; break; case CKD_SHA512_KDF: + case CKD_IBM_HYBRID_SHA512_KDF: *mech = CKM_SHA512; break; default: diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/common/verify_mgr.c opencryptoki-3.20.0+dfsg/usr/lib/common/verify_mgr.c --- opencryptoki-3.18.0+dfsg/usr/lib/common/verify_mgr.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/common/verify_mgr.c 2023-02-13 09:22:42.000000000 +0100 @@ -220,7 +220,9 @@ memset(ctx->context, 0x0, sizeof(RSA_DIGEST_CONTEXT)); } break; +#if !(NOMD2) case CKM_MD2_RSA_PKCS: +#endif case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: case CKM_SHA224_RSA_PKCS: @@ -363,7 +365,9 @@ ctx->context = NULL; break; #endif +#if !(NOMD2) case CKM_MD2_HMAC: +#endif case CKM_MD5_HMAC: if (mech->ulParameterLen != 0) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); @@ -433,7 +437,9 @@ goto done; } break; +#if !(NOMD2) case CKM_MD2_HMAC_GENERAL: +#endif case CKM_MD5_HMAC_GENERAL: { CK_MAC_GENERAL_PARAMS *param = @@ -445,11 +451,13 @@ rc = CKR_MECHANISM_PARAM_INVALID; goto done; } +#if !(NOMD2) if ((mech->mechanism == CKM_MD2_HMAC_GENERAL) && (*param > 16)) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); rc = CKR_MECHANISM_PARAM_INVALID; goto done; } +#endif if ((mech->mechanism == CKM_MD5_HMAC_GENERAL) && (*param > 16)) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); rc = CKR_MECHANISM_PARAM_INVALID; @@ -492,11 +500,13 @@ rc= CKR_MECHANISM_PARAM_INVALID; goto done; } +#if !(NOMD2) if ((mech->mechanism == CKM_MD2_HMAC_GENERAL) && (*param > 16)) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); rc = CKR_MECHANISM_PARAM_INVALID; goto done; } +#endif if ((mech->mechanism == CKM_MD5_HMAC_GENERAL) && (*param > 16)) { TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_PARAM_INVALID)); rc = CKR_MECHANISM_PARAM_INVALID; @@ -900,7 +910,9 @@ case CKM_RSA_PKCS_PSS: return rsa_pss_verify(tokdata, sess, ctx, in_data, in_data_len, signature, sig_len); +#if !(NOMD2) case CKM_MD2_RSA_PKCS: +#endif case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: case CKM_SHA224_RSA_PKCS: @@ -1021,7 +1033,9 @@ } switch (ctx->mech.mechanism) { +#if !(NOMD2) case CKM_MD2_RSA_PKCS: +#endif case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: case CKM_SHA224_RSA_PKCS: @@ -1112,7 +1126,9 @@ } switch (ctx->mech.mechanism) { +#if !(NOMD2) case CKM_MD2_RSA_PKCS: +#endif case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: case CKM_SHA224_RSA_PKCS: diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/config/cfgparse.y opencryptoki-3.20.0+dfsg/usr/lib/config/cfgparse.y --- opencryptoki-3.18.0+dfsg/usr/lib/config/cfgparse.y 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/config/cfgparse.y 2023-02-13 09:22:42.000000000 +0100 @@ -69,7 +69,7 @@ STRING_TOK %type configelemstar configelem barelist barelist_ne - eoc eocstar eocplus commentedconfigelemstar + eoc eocstar eocplus commentedconfigelemstar numpairlist %defines %destructor { free($$); } @@ -106,9 +106,9 @@ /* 0-n configuration elements with comments between them. */ configelemstar: - configelem configelemstar { $$ = confignode_append($1, $2); $1 = $2 = NULL; } - | - /* empty */ { $$ = NULL; } + configelem configelemstar { $$ = confignode_append($1, $2); $1 = $2 = NULL; } + | + /* empty */ { $$ = NULL; } /* Valid configuration elements: - "version" BARE @@ -135,80 +135,80 @@ care of all the positions where it wants to allow comments. */ configelem: - /* version somestring*/ + /* version somestring*/ FILEVERSION BARE eocstar { - struct ConfigFileVersionNode *n = confignode_allocfileversion($2, @1.first_line); - if (!n) { YYERROR; } - $$ = confignode_append(&(n->base), $3); - $2 = NULL; + struct ConfigFileVersionNode *n = confignode_allocfileversion($2, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), $3); + $2 = NULL; $3 = NULL; } | - /* conf = 42 */ - BARE EQUAL NUMBER eocstar { - struct ConfigIntValNode *n = confignode_allocintval($1, $3, @1.first_line); - if (!n) { YYERROR; } - $$ = confignode_append(&(n->base), $4); - $1 = NULL; + /* conf = 42 */ + BARE EQUAL NUMBER eocstar { + struct ConfigIntValNode *n = confignode_allocintval($1, $3, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), $4); + $1 = NULL; $4 = NULL; - } - | - /* conf = 1.0 */ - BARE EQUAL VERSION_TOK eocstar { - struct ConfigVersionValNode *n = confignode_allocversionval($1, $3, @1.first_line); - if (!n) { YYERROR; } - $$ = confignode_append(&(n->base), $4); - $1 = NULL; + } + | + /* conf = 1.0 */ + BARE EQUAL VERSION_TOK eocstar { + struct ConfigVersionValNode *n = confignode_allocversionval($1, $3, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), $4); + $1 = NULL; $4 = NULL; - } - | - /* conf = "A string" */ - BARE EQUAL STRING_TOK eocstar { - struct ConfigStringValNode *n = confignode_allocstringval($1, $3, @1.first_line); - if (!n) { YYERROR; } - $$ = confignode_append(&(n->base), $4); - $1 = NULL; - $3 = NULL; + } + | + /* conf = "A string" */ + BARE EQUAL STRING_TOK eocstar { + struct ConfigStringValNode *n = confignode_allocstringval($1, $3, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), $4); + $1 = NULL; + $3 = NULL; $4 = NULL; - } - | - /* conf = configuration */ - BARE EQUAL BARE eocstar { - struct ConfigBareValNode *n = confignode_allocbareval($1, $3, @1.first_line); - if (!n) { YYERROR; } - $$ = confignode_append(&(n->base), $4); - $1 = NULL; - $3 = NULL; + } + | + /* conf = configuration */ + BARE EQUAL BARE eocstar { + struct ConfigBareValNode *n = confignode_allocbareval($1, $3, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), $4); + $1 = NULL; + $3 = NULL; $4 = NULL; - } - | - /* conf 42 { subconf = 73 } */ - BARE NUMBER eocstar BEGIN_DEF commentedconfigelemstar END_DEF eocstar { - struct ConfigIdxStructNode *n = confignode_allocidxstruct($1, $2, $3, $5, @1.first_line); + } + | + /* conf 42 { subconf = 73 } */ + BARE NUMBER eocstar BEGIN_DEF commentedconfigelemstar END_DEF eocstar { + struct ConfigIdxStructNode *n = confignode_allocidxstruct($1, $2, $3, $5, @1.first_line); if (!n) { YYERROR; } - $$ = confignode_append(&(n->base), $7); - $1 = NULL; - $3 = $5 = $7 = NULL; - } - | - /* conf { subconf = 73 } */ - BARE eocstar BEGIN_DEF commentedconfigelemstar END_DEF eocstar { + $$ = confignode_append(&(n->base), $7); + $1 = NULL; + $3 = $5 = $7 = NULL; + } + | + /* conf { subconf = 73 } */ + BARE eocstar BEGIN_DEF commentedconfigelemstar END_DEF eocstar { - struct ConfigStructNode *n = confignode_allocstruct($1, $2, $4, @1.first_line); + struct ConfigStructNode *n = confignode_allocstruct($1, $2, $4, @1.first_line); if (!n) { YYERROR; } - $$ = confignode_append(&(n->base), $6); - $1 = NULL; - $2 = $4 = $6 = NULL; - } - | - /* conf ( A, B, C ) */ - BARE eocstar BEGIN_LIST barelist END_LIST eocstar { - struct ConfigBareListNode *n = confignode_allocbarelist($1, $2, $4, @1.first_line); + $$ = confignode_append(&(n->base), $6); + $1 = NULL; + $2 = $4 = $6 = NULL; + } + | + /* conf ( A, B, C ) */ + BARE eocstar BEGIN_LIST barelist END_LIST eocstar { + struct ConfigBareListNode *n = confignode_allocbarelist($1, $2, $4, @1.first_line); if (!n) { YYERROR; } - $$ = confignode_append(&(n->base), $6); - $1 = NULL; - $2 = $4 = $6 = NULL; - } + $$ = confignode_append(&(n->base), $6); + $1 = NULL; + $2 = $4 = $6 = NULL; + } | BARE eocstar { struct ConfigBareConstNode *n = confignode_allocbareconst($1, @1.first_line); @@ -217,18 +217,56 @@ $1 = NULL; $2 = NULL; } + | + /* A \n 1 2 B */ + BARE eocplus numpairlist BARE eocstar { + struct ConfigNumPairListNode *n = confignode_allocnumpairlist($1, $4, $2, $3, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), $5); + $1 = NULL; + $2 = NULL; + $3 = NULL; + $4 = NULL; + $5 = NULL; + } + | + STRING_TOK eocstar { + struct ConfigBareStringConstNode *n = confignode_allocbarestringconst($1, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), $2); + $1 = NULL; + $2 = NULL; + } + +/* +A list of number pairs. +*/ +numpairlist: + NUMBER NUMBER eocstar { + struct ConfigNumPairNode *n = confignode_allocnumpair($1, $2, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), $3); + $3 = NULL; + } + | + NUMBER NUMBER eocstar numpairlist { + struct ConfigNumPairNode *n = confignode_allocnumpair($1, $2, @1.first_line); + if (!n) { YYERROR; } + $$ = confignode_append(&(n->base), confignode_append($3, $4)); + $3 = $4 = NULL; + } /* A possibly empty list of barewords or comments. Two bare words have to be separated by a comma (see barelist_ne). */ barelist: - eocstar { $$ = $1; $1 = NULL; } - | - eocstar barelist_ne eocstar { - $$ = confignode_append($1, confignode_append($2, $3)); - $1 = $2 = $3 = NULL; - } + eocstar { $$ = $1; $1 = NULL; } + | + eocstar barelist_ne eocstar { + $$ = confignode_append($1, confignode_append($2, $3)); + $1 = $2 = $3 = NULL; + } /* Nonempty list of bare words. If the list contains multiple elements, they are separated by a comma. After a comma you can optionally add as many @@ -236,57 +274,57 @@ with a comma! */ barelist_ne: - BARE COMMA eocstar barelist_ne { - struct ConfigBareNode *n = confignode_allocbare($1, @1.first_line); - if (!n) { YYERROR; } - $1 = NULL; - $$ = confignode_append(&n->base, confignode_append($3, $4)); - $3 = $4 = NULL; - } - | - BARE { - struct ConfigBareNode *n = confignode_allocbare($1, @1.first_line); - if (!n) { YYERROR; } - $1 = NULL; - $$ = &n->base; - } + BARE COMMA eocstar barelist_ne { + struct ConfigBareNode *n = confignode_allocbare($1, @1.first_line); + if (!n) { YYERROR; } + $1 = NULL; + $$ = confignode_append(&n->base, confignode_append($3, $4)); + $3 = $4 = NULL; + } + | + BARE { + struct ConfigBareNode *n = confignode_allocbare($1, @1.first_line); + if (!n) { YYERROR; } + $1 = NULL; + $$ = &n->base; + } /* Either end of line comment or just end of line token. Either way, a line ends with this non-terminal. */ eoc: - COMMENT_TOK EOL { - if (trackComments) { - struct ConfigEOCNode *eocn = confignode_alloceoc($1, @1.first_line); - if (!eocn) { YYERROR; }; - $1 = NULL; - $$ = &eocn->base; + COMMENT_TOK EOL { + if (trackComments) { + struct ConfigEOCNode *eocn = confignode_alloceoc($1, @1.first_line); + if (!eocn) { YYERROR; }; + $1 = NULL; + $$ = &eocn->base; } else { - $$ = NULL; - } - } - | - EOL { - if (trackComments) { - struct ConfigEOCNode *eocn = confignode_alloceoc(NULL, @1.first_line); - if (!eocn) { YYERROR; }; - $$ = &eocn->base; + $$ = NULL; + } + } + | + EOL { + if (trackComments) { + struct ConfigEOCNode *eocn = confignode_alloceoc(NULL, @1.first_line); + if (!eocn) { YYERROR; }; + $$ = &eocn->base; } else { - $$ = NULL; - } - } + $$ = NULL; + } + } /* BNF form of eoc* */ eocstar: - eocplus { $$ = $1; $1 = NULL; } - | - /* empty */ { $$ = NULL; } + eocplus { $$ = $1; $1 = NULL; } + | + /* empty */ { $$ = NULL; } /* BNF form of eoc+ */ eocplus: - eoc { $$ = $1; $1 = NULL; } - | - eoc eocplus { $$ = confignode_append($1, $2); $1 = $2 = NULL; } + eoc { $$ = $1; $1 = NULL; } + | + eoc eocplus { $$ = confignode_append($1, $2); $1 = $2 = NULL; } %% @@ -295,13 +333,13 @@ int parse_configlib_file(FILE *conf, struct ConfigBaseNode **res, error_hook_f error_hook, int trackComments) { - configscan_t scanner; - int ret; + configscan_t scanner; + int ret; - configlex_init_extra(trackComments, &scanner); - configset_in(conf, scanner); - ret = configparse(scanner, res, error_hook, trackComments) ? -1 : 0; + configlex_init_extra(trackComments, &scanner); + configset_in(conf, scanner); + ret = configparse(scanner, res, error_hook, trackComments) ? -1 : 0; - configlex_destroy(scanner); - return ret; + configlex_destroy(scanner); + return ret; } diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/config/config.mk opencryptoki-3.20.0+dfsg/usr/lib/config/config.mk --- opencryptoki-3.18.0+dfsg/usr/lib/config/config.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/config/config.mk 2023-02-13 09:22:42.000000000 +0100 @@ -8,10 +8,10 @@ usr/lib/config/cfgparse.$(OBJEXT): usr/lib/config/cfglex.h usr/lib/config/cfgparse.c: usr/lib/config/cfgparse.y - $(AM_V_YACC)$(am__skipyacc) $(SHELL) $(YLWRAP) $< cfgparse.tab.c usr/lib/config/cfgparse.c cfgparse.tab.h usr/lib/config/cfgparse.h cfgparse.output usr/lib/config/cfgparse.output -- $(YACCCOMPILE) + $(AM_V_YACC)$(MKDIR_P) usr/lib/config && $(am__skipyacc) $(SHELL) $(YLWRAP) $< cfgparse.tab.c usr/lib/config/cfgparse.c cfgparse.tab.h usr/lib/config/cfgparse.h cfgparse.output usr/lib/config/cfgparse.output -- $(YACCCOMPILE) usr/lib/config/cfglex.c: usr/lib/config/cfglex.l - $(AM_V_LEX)$(am__skiplex) $(SHELL) $(YLWRAP) $< lex.config.c usr/lib/config/cfglex.c cfglex.h usr/lib/config/cfglex.h -- $(LEXCOMPILE) + $(AM_V_LEX)$(MKDIR_P) usr/lib/config && $(am__skiplex) $(SHELL) $(YLWRAP) $< lex.config.c usr/lib/config/cfglex.c cfglex.h usr/lib/config/cfglex.h -- $(LEXCOMPILE) CLEANFILES += usr/lib/config/cfglex.c usr/lib/config/cfglex.h \ usr/lib/config/cfgparse.c usr/lib/config/cfgparse.h \ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/config/configuration.c opencryptoki-3.20.0+dfsg/usr/lib/config/configuration.c --- opencryptoki-3.18.0+dfsg/usr/lib/config/configuration.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/config/configuration.c 2023-02-13 09:22:42.000000000 +0100 @@ -53,6 +53,15 @@ case CT_BARECONST: confignode_freebareconst(confignode_to_bareconst(n)); break; + case CT_NUMPAIR: + confignode_freenumpair(confignode_to_numpair(n)); + break; + case CT_NUMPAIRLIST: + confignode_freenumpairlist(confignode_to_numpairlist(n)); + break; + case CT_BARESTRINGCONST: + confignode_freebarestringconst(confignode_to_barestringconst(n)); + break; default: break; } @@ -151,6 +160,63 @@ fprintf(fp, "%s = %lu", n->base.key, n->value); } +static void confignode_dumpnumpair(FILE *fp, struct ConfigNumPairNode *n, + unsigned flags) +{ + if (flags & CONFIG_FLAG_INT_PRINT_MODE_HEX) + fprintf(fp, "0x%lx 0x%lx", n->value1, n->value2); + else + fprintf(fp, "%lu %lu", n->value1, n->value2); +} + +static void confignode_dumpnumpairlist(FILE *fp, + struct ConfigNumPairListNode *n, + struct ConfigDumpCb *cb, + unsigned flags, unsigned indent, + unsigned curindent) +{ + struct ConfigBaseNode *i; + int f, atbol = 1; + + fputs(n->base.key, fp); + if (n->beforeFirst) + atbol = confignode_dump_i(fp, n->beforeFirst, cb, flags, indent, + curindent, 0, 0); + if (!atbol) + fputc('\n', fp); + + if (n->value) { + confignode_foreach(i, n->value, f) { + switch (i->type) { + case CT_NUMPAIR: + if (atbol) + confignode_dump_indent(fp, curindent + indent); + atbol = 0; + confignode_dumpnumpair(fp, confignode_to_numpair(i), flags); + break; + + case CT_EOC: + if (i->key) { + if (atbol) + fprintf(fp, "#%s", i->key); + else + fprintf(fp, " #%s", i->key); + } + fputc('\n', fp); + atbol = 1; + break; + + default: + break; + } + } + } + if (!atbol) + fputc('\n', fp); + confignode_dump_indent(fp, curindent); + fputs(n->end, fp); +} + static int confignode_dump_i(FILE *fp, struct ConfigBaseNode *n, struct ConfigDumpCb *cb, unsigned flags, unsigned indent, unsigned curindent, @@ -165,14 +231,18 @@ if (cb) { flags = cb->flags(i, flags); } - if (atbol) + if (atbol) { confignode_dump_indent(fp, curindent); - else if (i->type != CT_EOC) + if (curindent != 0) + atbol = 0; + } else if (i->type != CT_EOC) { /* In this case, we did not indent, but if a user writes multiple configurations in one line, we will concatenate value of previous item with key of new item producing an invalid configuration. So add a space. */ fputc(' ', fp); + } + switch (i->type) { case CT_FILEVERSION: fprintf(fp, "version %s", i->key); @@ -229,6 +299,19 @@ case CT_BARECONST: fputs(i->key, fp); break; + case CT_NUMPAIR: + if (atbol) + confignode_dump_indent(fp, curindent); + confignode_dumpnumpair(fp, confignode_to_numpair(i), flags); + break; + case CT_NUMPAIRLIST: + confignode_dumpnumpairlist(fp, confignode_to_numpairlist(i), cb, + flags, indent, curindent); + newatbol = 1; + break; + case CT_BARESTRINGCONST: + fprintf(fp, "\"%s\"", i->key); + break; default: break; } @@ -521,3 +604,79 @@ } return res; } + +struct ConfigNumPairNode * +confignode_allocnumpairdumpable(unsigned long value1, unsigned long value2, + int line, char *comment) +{ + struct ConfigNumPairNode *res; + struct ConfigEOCNode *eoc; + + res = confignode_allocnumpair(value1, value2, line); + if (res) { + eoc = confignode_alloceoc(comment ? strdup(comment) : NULL, line); + if (eoc) { + confignode_append(&(res->base), &(eoc->base)); + } else { + confignode_freenumpair(res); + res = NULL; + } + } + return res; +} + +struct ConfigNumPairListNode * +confignode_allocnumpairlistdumpable(char *key, char* end, + struct ConfigBaseNode *beforeFirst, + struct ConfigBaseNode *value, + int line, char *comment) +{ + struct ConfigNumPairListNode *res = NULL; + struct ConfigEOCNode *eoc; + char *dkey, *dend; + + dkey = strdup(key); + if (!dkey) + return NULL; + dend = strdup(end); + if (!dend) { + free(dkey); + return NULL; + } + /* First allocate eoc node such that if allocating res fails, we do not + take ownership of beforeOpen or value. */ + eoc = confignode_alloceoc(comment ? strdup(comment) : NULL, line); + if (eoc) { + res = confignode_allocnumpairlist(dkey, dend, beforeFirst, value, line); + if (res) { + confignode_append(&(res->base), &(eoc->base)); + } else { + confignode_freeeoc(eoc); + free(dkey); + free(dend); + } + } else { + free(dkey); + free(dend); + } + return res; +} + +struct ConfigBareStringConstNode * +confignode_allocbarestringconstdumpable(char *key, int line, char *comment) +{ + struct ConfigBareStringConstNode *res; + struct ConfigEOCNode *eoc; + + res = confignode_allocbarestringconst(key, line); + if (res) { + eoc = confignode_alloceoc(comment ? strdup(comment) : NULL, line); + if (eoc) { + confignode_append(&(res->base), &(eoc->base)); + } else { + confignode_freebarestringconst(res); + res = NULL; + } + } + return res; +} diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/config/configuration.h opencryptoki-3.20.0+dfsg/usr/lib/config/configuration.h --- opencryptoki-3.18.0+dfsg/usr/lib/config/configuration.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/config/configuration.h 2023-02-13 09:22:42.000000000 +0100 @@ -64,6 +64,19 @@ * represents its own configuration element. */ #define CT_BARECONST (1u << 10u) +/* + * A pair of numbers + */ +#define CT_NUMPAIR (1u << 11u) +/* + * A list of number pairs + */ +#define CT_NUMPAIRLIST (1u << 12u) +/* + * A bare quoted string constant, i.e., a bare string outside of a list that + * represents its own configuration element. + */ +#define CT_BARESTRINGCONST (1u << 13u) /* * Mask for all types that have a key. This excludes FILEVERSION, @@ -71,7 +84,7 @@ */ #define CT_HAS_KEY_MASK (CT_INTVAL | CT_STRINGVAL | CT_VERSIONVAL | \ CT_BAREVAL | CT_STRINGVAL | CT_IDX_STRUCT | \ - CT_BARELIST | CT_BARECONST) + CT_BARELIST | CT_BARECONST | CT_NUMPAIRLIST | CT_BARESTRINGCONST) /***** Node Types *****/ struct ConfigBaseNode; @@ -142,6 +155,24 @@ struct ConfigBaseNode base; }; +struct ConfigNumPairNode { + struct ConfigBaseNode base; + unsigned long value1; + unsigned long value2; +}; + +struct ConfigNumPairListNode { + struct ConfigBaseNode base; + struct ConfigBaseNode *beforeFirst; + /* either a ConfigNumPairNode or a ConfigEOCNode */ + struct ConfigBaseNode *value; + char *end; +}; + +struct ConfigBareStringConstNode { + struct ConfigBaseNode base; +}; + /* Casting from base type functions */ static inline struct ConfigFileVersionNode * confignode_to_fileversion(struct ConfigBaseNode *n) @@ -220,6 +251,27 @@ (((char *)n) - offsetof(struct ConfigBareConstNode, base)); } +static inline struct ConfigNumPairNode * +confignode_to_numpair(struct ConfigBaseNode *n) +{ + return (struct ConfigNumPairNode *) + (((char *)n) - offsetof(struct ConfigNumPairNode, base)); +} + +static inline struct ConfigNumPairListNode * +confignode_to_numpairlist(struct ConfigBaseNode *n) +{ + return (struct ConfigNumPairListNode *) + (((char *)n) - offsetof(struct ConfigNumPairListNode, base)); +} + +static inline struct ConfigBareStringConstNode * +confignode_to_barestringconst(struct ConfigBaseNode *n) +{ + return (struct ConfigBareStringConstNode *) + (((char *)n) - offsetof(struct ConfigBareStringConstNode, base)); +} + /* Freeing functions */ /** @@ -331,6 +383,34 @@ } } +static inline void confignode_freenumpair(struct ConfigNumPairNode *n) +{ + if (n) { + free(n->base.key); + free(n); + } +} + +static inline void confignode_freenumpairlist(struct ConfigNumPairListNode *n) +{ + if (n) { + free(n->base.key); + confignode_deepfree(n->beforeFirst); + confignode_deepfree(n->value); + free(n->end); + free(n); + } +} + +static inline void confignode_freebarestringconst( + struct ConfigBareStringConstNode *n) +{ + if (n) { + free(n->base.key); + free(n); + } +} + /* Allocation functions */ static inline struct ConfigFileVersionNode * @@ -518,6 +598,63 @@ return res; } +static inline struct ConfigNumPairNode *confignode_allocnumpair( + unsigned long value1, + unsigned long value2, + int line) +{ + struct ConfigNumPairNode *res = malloc(sizeof(struct ConfigNumPairNode)); + + if (res) { + res->base.next = res->base.prev = &(res->base); + res->base.key = NULL; + res->base.type = CT_NUMPAIR; + res->base.line = line; + res->base.flags = 0; + res->value1 = value1; + res->value2 = value2; + } + return res; +} + +static inline struct ConfigNumPairListNode * +confignode_allocnumpairlist(char *key, char *end, + struct ConfigBaseNode *beforeFirst, + struct ConfigBaseNode *value, + int line) +{ + struct ConfigNumPairListNode *res = malloc(sizeof(struct ConfigNumPairListNode)); + + if (res) { + res->base.next = res->base.prev = &(res->base); + res->base.key = key; + res->base.type = CT_NUMPAIRLIST; + res->base.line = line; + res->base.flags = 0; + res->beforeFirst = beforeFirst; + res->value = value; + res->end = end; + } + return res; +} + +static inline struct ConfigBareStringConstNode *confignode_allocbarestringconst( + char *key, + int line) +{ + struct ConfigBareStringConstNode *res = + malloc(sizeof(struct ConfigBareStringConstNode)); + + if (res) { + res->base.next = res->base.prev = &(res->base); + res->base.key = key; + res->base.type = CT_BARESTRINGCONST; + res->base.line = line; + res->base.flags = 0; + } + return res; +} + /* Convenience functions for AST manipulation. These functions automatically append an EOC-node to the correct node which optionally includes a comment. If no comment is desired, simply @@ -565,6 +702,16 @@ struct ConfigBareConstNode * confignode_allocbareconstdumpable(char *key, int line, char *comment); +struct ConfigNumPairNode * +confignode_allocnumpairdumpable(unsigned long value1, unsigned long value2, + int line, char *comment); + +struct ConfigNumPairListNode * +confignode_allocnumpairlistdumpable(char *key, char* end, + struct ConfigBaseNode *beforeFirst, + struct ConfigBaseNode *value, + int line, char *comment); + /* Append the list n2 to the end of the list n1. NULL is considered as empty list. */ static inline struct ConfigBaseNode *confignode_append(struct ConfigBaseNode *n1, @@ -609,7 +756,7 @@ * f is an integer */ #define confignode_foreach(i,c,f) \ - for((i)=(c),(f)=1;(f)||(i)!=(c);(i)=(i)->next,(f)=0) + for((i)=(c),(f)=1;(i)&&((f)||(i)!=(c));(i)=(i)->next,(f)=0) static inline struct ConfigBaseNode * confignode_find(struct ConfigBaseNode *cfg, const char *key) diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11adm.h opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11adm.h --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11adm.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11adm.h 2023-02-13 09:22:42.000000000 +0100 @@ -1,49 +1,18 @@ /* - * COPYRIGHT (c) International Business Machines Corp. 2020 + * (C) Copyright IBM Corp. 2012, 2022 * * This program is provided under the terms of the Common Public License, * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this * software constitutes recipient's acceptance of CPL-1.0 terms which can be * found in the file LICENSE file or at * https://opensource.org/licenses/cpl1.0.php - */ - -/*---------------------------------------------------------------------- - * This EP11 header file is distributed under the following license - * - * Copyright 2020 IBM Corp. All Rights Reserved - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * - * 1. Redistributions of source code must retain the above copyright notice, - * this list of conditions and the following disclaimer. - * - * 2. Redistributions in binary form must reproduce the above copyright notice, - * this list of conditions and the following disclaimer in the documentation - * and/or other materials provided with the distribution. - * - * 3. Neither the name of the copyright holder nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, - * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, - * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, - * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; - * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, - * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR - * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF - * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * *---------------------------------------------------------------------- * EP11 service mail address: EP11SERV@de.ibm.com * * Use this mail address for Bugs and Comments with the EP11 product. - *----------------------------------------------------------------------*/ + *---------------------------------------------------------------------- + */ #if ! defined(__xcpadm_h__) #define __xcpadm_h__ @@ -56,34 +25,6 @@ #error "We need types, please include before this file." #endif -// these numbers apply to current version, subject to change -// Please note that this defines are DEPRECATED. Please use their XCP_* -// counterpart in ep11.h -// -#if !defined(EP11_SERIALNR_CHARS) -#define EP11_SERIALNR_CHARS XCP_SERIALNR_CHARS -#endif - -#if !defined(EP11_KEYCSUM_BYTES) -/* full size of verific. pattern */ -#define EP11_KEYCSUM_BYTES XCP_KEYCSUM_BYTES -#endif - -#if !defined(EP11_ADMCTR_BYTES) -/* admin transaction ctrs */ -#define EP11_ADMCTR_BYTES XCP_ADMCTR_BYTES -#endif - -#if !defined(EP11_ADM_REENCRYPT) -/* transform blobs to next WK */ -#define EP11_ADM_REENCRYPT XCP_ADM_REENCRYPT -#endif - -#if !defined(CK_IBM_EP11Q_DOMAIN) -/* list domain's WK hashes */ -#define CK_IBM_EP11Q_DOMAIN CK_IBM_XCPQ_DOMAIN -#endif -// end of DEPRECATED defines //------------------------------------- // flags common to all functions that have a flag parameter @@ -131,13 +72,22 @@ #define DOMAIN_MASK_LENGTH XCP_DOMAINS/8 // space for 256 domains - +//------------------------------------- +// Key-Part-Holder template +// contain credentials of a key-part holder. Those credentials +// can be file based and/or smart card based references. struct KPH { - const unsigned char *cert; - size_t clen; - const char *id; - const char *pw; - const char *kpfname; + const unsigned char *cert; // certificate + size_t clen; // certificate length + const char *id; // private key + const char *pw; // private key passphrase + const char *kpfname; // filename of the key-part + char scard; // indicates a smart card user + char ski_id; // subject key identifier ID + int rdr_id; // smart card reader number + char kp_id; // key-part ID + uint64_t sigmech; // signature mechenism + const char *padmode; // padding mode } ; @@ -190,30 +140,6 @@ #define XCP_ADMRESP_INIT0 { 0,0,0, {0},{0},{0}, {0}, CKR_OK, 0, NULL,0, } -// ep11_admresp_t is DEPRECATED. Please use XCPadmresp_t directly -typedef struct ep11_admresp { - uint32_t fn; - uint32_t domain; - uint32_t domainInst; - - /* module ID || module instance */ - unsigned char module[ EP11_SERIALNR_CHARS + EP11_SERIALNR_CHARS ]; - unsigned char modNr[ EP11_SERIALNR_CHARS ]; - unsigned char modInst[ EP11_SERIALNR_CHARS ]; - - unsigned char tctr[ EP11_ADMCTR_BYTES ]; /* transaction counter */ - - CK_RV rv; - uint32_t reason; - - // points to original response; NULL if no payload - // make sure it's copied if used after releasing response block - // - const unsigned char *payload; - size_t pllen; -} *ep11_admresp_t; - - //------------------------------------- // listing of CP modes with their respective sets of control points that are // either required or prohibited @@ -239,7 +165,7 @@ { XCP_ADMS_FIPS2011, "fips2011", 3, { XCP_CPB_ALG_NFIPS2011, XCP_CPB_KEYSZ_80BIT, - XCP_CPB_KEYSZ_RSA65536 }, + XCP_CPB_KEYSZ_RSA65536, }, 0, { }, }, @@ -279,6 +205,37 @@ XCP_CPB_ALG_EC_NISTCRV, XCP_CPB_ALG_NFIPS2011, XCP_CPB_ALG_NBSI2011, XCP_CPB_ALG_DH, XCP_CPB_DERIVE }, + }, + { XCP_ADMS_FIPS2021, "fips2021", + 15, + { XCP_CPB_ALG_NFIPS2011, XCP_CPB_KEYSZ_80BIT, + XCP_CPB_KEYSZ_RSA65536, + XCP_CPB_ALG_NFIPS2021, XCP_CPB_ALG_EC_25519, + XCP_CPB_ALG_PQC, XCP_CPB_BTC, + XCP_CPB_ECDSA_OTHER, XCP_CPB_ALLOW_NONSESSION, + XCP_CPB_ALG_EC_SECGCRV, XCP_CPB_ALG_EC_BPOOLCRV, + XCP_CPB_COMPAT_LEGACY_SHA3, XCP_CPB_DSA_PARAMETER_GEN, + XCP_CPB_WRAP_ASYMM, XCP_CPB_UNWRAP_ASYMM + }, + 0, + { }, + }, + { XCP_ADMS_FIPS2024, "fips2024", + 16, + { XCP_CPB_ALG_NFIPS2011, XCP_CPB_KEYSZ_80BIT, + XCP_CPB_KEYSZ_RSA65536, + XCP_CPB_ALG_NFIPS2021, XCP_CPB_ALG_EC_25519, + XCP_CPB_ALG_PQC, XCP_CPB_BTC, + XCP_CPB_ECDSA_OTHER, XCP_CPB_ALLOW_NONSESSION, + XCP_CPB_ALG_EC_SECGCRV, XCP_CPB_ALG_EC_BPOOLCRV, + XCP_CPB_ALG_NFIPS2024, XCP_CPB_COMPAT_LEGACY_SHA3, + XCP_CPB_DSA_PARAMETER_GEN, XCP_CPB_WRAP_ASYMM, + XCP_CPB_UNWRAP_ASYMM + }, + 0, + { }, + // XCP_ADMS_ADM_FIPS2021 is not reported here as it is not set with + // control points } } ; @@ -381,7 +338,7 @@ //------------------------------------- -// Queries the current WK for the given target +// Queries the current/next WK for the given target // // WK Hash is returned in (*wk, wlen) on success if wk is not NULL // @@ -396,7 +353,7 @@ // // Uses xcpa_queryblock() - See function header for possible return codes // -long xcpa_query_wk(unsigned char *wk, size_t wlen, target_t target) ; +long xcpa_query_wk(unsigned char *wk, size_t wlen, int type, target_t target) ; //------------------------------------- @@ -695,12 +652,13 @@ //------------------------------------- // get compliance mode from CP set (see ep11_cpt_modes[] for possible compliance // modes) +// can not check for administrative compliance modes // // cps CP set of XCP_CP_BYTES length, see xcpa_query_cps // // returns >0 compliance mode (see XCP_ADMS_...) // -// does not verify CP set! +// does not verify CP set // uint32_t xcpa_cps2compliance(const unsigned char *cps /* XCP_CP_BYTES */) ; @@ -837,8 +795,12 @@ // EC only: RSA recipients must keep these lengths 0 // // largest supported curve: P-521 + unsigned char srcprivate[ 66 ]; /* private key (PKCS#8) */ + size_t sprivlen; /* priv. key byte count */ + unsigned char *oid; /* EC curve OID */ + size_t olen; /* EC curve OID length */ unsigned char srcpublic[ 1+66+66 ]; /* originator public point */ - size_t splen; /* pub.point bytecount */ + size_t splen; /* pub. point bytecount */ unsigned char ukm[ XCP_RI_UKM_BYTES ]; /* user keymaterial */ size_t ulen; @@ -853,7 +815,7 @@ int ktype; /* one of the wire-specified types */ CK_MECHANISM *alg; /* currently, ignored */ - + unsigned char wrap_alg[25]; /* AES Key Wrap algorithm OID */ // largest supported importer type: 4096-bit RSA unsigned char raw[ 4096/8 ]; /* actual encrypted bytes */ size_t rlen; @@ -861,6 +823,15 @@ //------------------------------------- +// Recipient info used for encrypted key part transport +// +typedef struct Recipient_info { + uint32_t version; /* struct version */ + unsigned char data[ 1024 ]; /* ASN.1 encoded recipient info */ + size_t dlen; /* length of recipient info */ +} *Recipient_info_t; + +//------------------------------------- // turn user key material (UKM), target key bitcount, wrapping alg into // RFC 3278 SharedInfo structure // @@ -906,15 +877,15 @@ //------------------------------------- -// reads ASN.1 formated RecipientInfo (asn) and turns it into encr structure +// reads ASN.1 formatted RecipientInfo (asn) and turns it into rinfo structure // -// returns size of RecipientInfo if asn could be read and encr (if non NULL) -// could be filed. Otherwise return failure. +// returns size of RecipientInfo if asn could be read and rinfo (if non NULL) +// could be filled. Otherwise return failure. // -// xcp_rcptinfo_read() can not always recognize the exact importer key type, -// because some EC public keys have the same size. If a brainpool and a NIST -// curve have the same public key size the brainpool curve is prefered and -// returned +// Note: Depending on the ASN.1 information xcp_rcptinfo_read() may not +// necessarily update all available fields of the Encrdkey structure. +// It will not wipe the Encrdkey structure before, hence it may contain +// unfilled sections. It's recommended to provide a zeroized Encrdkey struct. // // possible error return codes: // XCP_EARG: missing RecipientInfo @@ -1023,6 +994,15 @@ //------------------------------------- +// returns net bytecount (full T+L+V) if start of (asn,alen) is full tag +// 0 if invalid +// +// sets *voffs to T+L bytecount if non-NULL +// +size_t xcpa_asn_tag(size_t *voffs, const unsigned char *asn, size_t alen); + + +//------------------------------------- // return raw bytecount of ASN.1 SEQ // return XCP_EINVALID if malformed and XCP_ESIZE if ASN.1 lengths are not // correct @@ -1039,6 +1019,18 @@ //------------------------------------- +// nonzero tag is compared to that of (asn,alen) +// returns T+L+V bytecount in case of success +// XCP_EINVALID if asn is malformed +// XCP_EARG if asn or alen arguments are invalid +// XCP_ESIZE if ASN.1 lengths are not correct +// +long xcpa_asn_tlv (const void *asn, size_t alen, + unsigned int tag, size_t *voffset, + size_t *vbytes); + + +//------------------------------------- // DH ASN.1 SEQ's need to be split up, since we only need public value (X) // full input is (potentially MACed) DH SPKI // @@ -1133,21 +1125,24 @@ // Constructs key part file with ASN.1 envelope // writes output to (*reqprep, reqpreplen) // -// statesave contains the target domain mask +// domainmask target domain mask // kphs keypart holder certificates // kcnt number of kphs // ekps contains re-encrypted keyparts // reqprep output buffer // reqpreplen output length +// headerinfo set to 0 if no header info requested +// set to 1 if header info requested // // returns 0 if successful // <0 if something fails -long xcpa_construct_keypart_file(struct STATESAVE *statesave, - const struct KPH *kphs, - const struct Encrdkey *ekps, - unsigned int kcnt, - unsigned char *reqprep, - size_t *reqpreplen); +long xcpa_construct_keypart_file(unsigned char *domainmask, + const struct KPH *kphs, + const struct Encrdkey *ekps, + unsigned int kcnt, + unsigned char *reqprep, + size_t *reqpreplen, + unsigned int headerinfo); //------------------------------------- @@ -1162,6 +1157,18 @@ //------------------------------------- +// Enable export state permission +// +// target target module/domain +// sign_cb provide the callback for generating signatures +// may be NULL if no signatures required +// signopts number of signatures requested +// +long xcpa_enable_export_state(target_t target, + xcpa_admin_signs_cb_t sign_cb, const void *signopts); + + +//------------------------------------- // Enable import WK permission // // target target domain @@ -1173,10 +1180,23 @@ //------------------------------------- +// Enable import state permission +// +// target target module/domain +// sign_cb provide the callback for generating signatures +// may be NULL if no signatures required +// signopts number of signatures requested +// +long xcpa_enable_import_state(target_t target, + xcpa_admin_signs_cb_t sign_cb, const void *signopts); + + +//------------------------------------- // Export the domain WK of the given target // writes output to (*resp, resplen) // // target addresses target module/domain +// wktype indicates either current or next WK // keyparts pointer to the encrypted keyparts // keypartlen length of encrypted keyparts // request pointer to the export request data @@ -1184,14 +1204,52 @@ // sign_cb provide the callback for generating signatures // may be NULL if no signatures required // signopts number of signatures requested -long xcpa_export_wk(target_t target, +long xcpa_export_wk(target_t target, int wktype, unsigned char *keyparts, size_t *keypartlen, const unsigned char *request, size_t requestlen, xcpa_admin_signs_cb_t sign_cb, const void *signopts); //------------------------------------- -// Import a domain WK to the given target +// Export the state of the given target +// writes output to (*state/statelen, tkps/tkpslen) +// +// target addresses target module/domain +// state pointer to exported state data +// statelen length of exported state data +// keyparts pointer to transport keyparts +// keypartlen length of transport keyparts +// request pointer to the export request +// requestlen length of export request +// sign_cb provide the callback for generating signatures +// may be NULL if no signatures required +// signopts number of signatures requested +// +long xcpa_export_state(target_t target, + unsigned char *state, size_t *statelen, + unsigned char *tkps, size_t *tkplen, + const unsigned char *request, size_t requestlen, + xcpa_admin_signs_cb_t sign_cb, const void *signopts); + + +//------------------------------------- +// Import a domain WK (from recipient info) to the given target +// +// target addresses target module/domain +// rinfo contains recipient infos +// ricnt number of recipient infos +// wkvp WK verification pattern +// sign_cb provide the callback for generating signatures +// may be NULL if no signatures required +// signopts number of signatures requested +long xcpa_import_wk_rcptinfo(target_t target, + struct Recipient_info *rinfo, unsigned int ricnt, + const unsigned char *wkvp, + xcpa_admin_signs_cb_t sign_cb, const void *signopts); + + +//------------------------------------- +// Import a domain WK (from ekps struct) to the given target // // target addresses target module/domain // ekps contains re-encrypted keyparts @@ -1205,6 +1263,26 @@ xcpa_admin_signs_cb_t sign_cb, const void *signopts); + +//------------------------------------- +// Import module state data to a target +// +// target addresses target module +// domainmask list of affected domains +// ekps contains re-encrypted keyparts +// kpcnt number of keyparts +// state module state data +// statelen state data len +// sign_cb provide the callback for generating signatures +// may be NULL if no signatures required +// signopts number of signatures requested +// +long xcpa_import_state(target_t target, unsigned char *domainmask, + unsigned char *state, size_t statelen, + struct Encrdkey *ekps, unsigned int kpcnt, + xcpa_admin_signs_cb_t sign_cb, const void *signopts); + + //------------------------------------- // Commit a domain WK of the given target // @@ -1226,6 +1304,18 @@ //------------------------------------- +// Generate a random WK for the given target +// +// target addresses target module/domain +// wkvp WK verification pattern +// sign_cb provide the callback for generating signatures +// may be NULL if no signatures required +// signopts number of signatures requested +long xcpa_gen_random_wk(target_t target, unsigned char *wkvp, + xcpa_admin_signs_cb_t sign_cb, const void *signopts); + + +//------------------------------------- // SKI-based SignerInfo form // // 30(02(03) // v3: signer identified by SKI @@ -1319,62 +1409,106 @@ -//---------------------------------------------------------------------- -// The following functions are DEPRECTATED! -// for return values see their xcpa_* counterpart + +/* + * Parse the list of indices and ranges and construct corresponding bitmask + * args pointer to a comma separated list of indices + * (ranges of indices are also allowed) + * mask pointer to an 32 byte array that represents our domain mask + * masksize bit-length of the mask + */ +int xcp_args2mask(char *args, unsigned char *mask, int masksize); + + +/* + * Fills in 'file-ID', 'offset' and 'length' parameter into the file header + * hdr pointer to the file header + * hlen length of the header + * fileid fileid to refer the file type + * offset offset of data pointer + * bytes number of bytes to transfer + */ +int xcpa_write_filepart_hdr(unsigned char *hdr, size_t hlen, + uint32_t fileid, uint32_t offset, + uint32_t bytes); -/*---------------------------------------------------------------------- - * build a command block to (blk,blen), querying 'fn' - * (payload,plen) copied to query block if non-NULL +/* reads partial data from target/fileid + * returning payload to res, rlen * - * returns written bytecount; size query if blk is NULL - * *minf used for module ID and transaction counter - * ignored for commands where those fields are ignored + * returns >0 on success (bytecount) + * 0 if file access failed (not available, etc.) + * <0 if anything unexpected failed */ -long ep11a_cmdblock(unsigned char *blk, size_t blen, - unsigned int fn, - const struct ep11_admresp *minf, - const unsigned char *tctr, /* EP11_ADMCTR_BYTES */ - const unsigned char *payload, size_t plen) - __attribute__ ((deprecated)) ; +long xcpa_query_filepart(unsigned char *res, size_t rlen, + const unsigned char *hdr, size_t hlen, + target_t target, + CK_RV exprv); + + +/* reads complete data from target/fileid + * returning payload to res, rlen + * + * returns >0 on success (bytecount) + * 0 if file access failed (not available, etc.) + * <0 if anything unexpected failed + */ +long xcpa_query_full_file(unsigned char *res, size_t rlen, + target_t target, + unsigned int fileid, + unsigned int block); + +/* writes data to internal files + * takes data, dlen to write to target/fileid + * + * returns >0 if results have been all written + * <0 if anything unexpected failed + */ +long xcpa_write_full_file(target_t target, + xcpa_admin_signs_cb_t sign_cb, const void *signopts, + const unsigned char *data, size_t dlen, + unsigned int fileid, unsigned int block); -/*---------------------------------------------------------------------- - * returns <0 if response is malformed, or contents invalid + +long xcpa_remove_file(target_t target, unsigned int fileid, + xcpa_admin_signs_cb_t sign_cb, const void *signopts); + + +/* brute-force section parser: enumerate all encrypted-KP sections + * + * returns >0 offset of full OCTET STRING T+L+V section + * 0 when there are no more sections + * <0 if encoding is invalid (which SNH) * - * parse embedded return value from response, writes to *rv if non-NULL - * (outside envelope always reports CKR_OK, unless infrastructure - * failed) + * sets *kpidx to index (sub-type) of keypart found if not NULL + * + * since external compound is SEQUENCE, it can't match KP at offset 0 + * therefore, comparing > is correct */ -long ep11a_internal_rv(const unsigned char *rsp, size_t rlen, - struct ep11_admresp *rspblk, CK_RV *rv) - __attribute__ ((deprecated)) ; +long xcpa_kp_next_section(const unsigned char *kps, size_t kplen, + unsigned long idx, uint32_t *kpidx); -/*---------------------------------------------------------------------- - * in: [0] query type - * out: [0] packed info structure +/* retrieve recipient infos from keypart sections * - * outputs are fixed size, except CK_IBM_XCPQ_DOMAINS, which returns a - * list therefore, infbytes is ignored by other types (we still check - * if present) + * returns >0 number of recipient infos found + * <0 if anything failed */ -CK_RV m_get_ep11_info(CK_VOID_PTR pinfo, CK_ULONG_PTR infbytes, - unsigned int query, - unsigned int subquery, - target_t target) - __attribute__ ((deprecated)) ; +long xcpa_kps_retrieve_rcptinfo(struct Recipient_info *rcpti, + unsigned int rimax, + const unsigned char *kpexport, + size_t kplen); /* - * Parse the list of indices and ranges and construct corresponding bitmask - * args pointer to a comma separated list of indices - * (ranges of indices are also allowed) - * mask pointer to an 32 byte array that represents our domain mask - * masksize bit-length of the mask + * report domain compliance + * + * returns compliance bitmask if successful and 0 if anything failed + * (as zero is invalid as we always have a default compliance active) + * */ -int xcp_args2mask(char *args, unsigned char *mask, int masksize); +uint64_t get_dom_compl(target_t target); #endif /* !defined(__xcpadm_h__) */ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11cpfilter.conf opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11cpfilter.conf --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11cpfilter.conf 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11cpfilter.conf 2023-02-13 09:22:42.000000000 +0100 @@ -25,13 +25,13 @@ XCP_CPB_SIGN_ASYMM: CKM_RSA_PKCS, CKM_RSA_PKCS_PSS, CKM_SHA1_RSA_X9_31, CKM_SHA1_RSA_PKCS, CKM_SHA1_RSA_PKCS_PSS, CKM_SHA256_RSA_PKCS, CKM_SHA256_RSA_PKCS_PSS, CKM_SHA224_RSA_PKCS, CKM_SHA224_RSA_PKCS_PSS, CKM_SHA384_RSA_PKCS, CKM_SHA384_RSA_PKCS_PSS, CKM_SHA512_RSA_PKCS, CKM_SHA512_RSA_PKCS_PSS, CKM_ECDSA, CKM_ECDSA_SHA1, CKM_DSA, CKM_DSA_SHA1, CKM_RSA_X9_31, CKM_ECDSA_SHA224, CKM_ECDSA_SHA256, CKM_ECDSA_SHA384, CKM_ECDSA_SHA512 # encrypt with symmetric keys -XCP_CPB_ENCRYPT_SYMM: CKM_AES_ECB, CKM_AES_CBC, CKM_AES_CBC_PAD, CKM_DES3_ECB, CKM_DES3_CBC, CKM_DES3_CBC_PAD, CKM_DES_ECB, CKM_DES_CBC +XCP_CPB_ENCRYPT_SYMM: CKM_AES_ECB, CKM_AES_CBC, CKM_AES_CBC_PAD, CKM_DES3_ECB, CKM_DES3_CBC, CKM_DES3_CBC_PAD, CKM_DES_ECB, CKM_DES_CBC, CKM_AES_XTS #decrypt with private keys XCP_CPB_DECRYPT_ASYMM: CKM_RSA_PKCS # decrypt with symmetric keys -XCP_CPB_DECRYPT_SYMM: CKM_AES_ECB, CKM_AES_CBC, CKM_AES_CBC_PAD, CKM_DES3_ECB, CKM_DES3_CBC, CKM_DES3_CBC_PAD, CKM_DES_ECB, CKM_DES_CBC +XCP_CPB_DECRYPT_SYMM: CKM_AES_ECB, CKM_AES_CBC, CKM_AES_CBC_PAD, CKM_DES3_ECB, CKM_DES3_CBC, CKM_DES3_CBC_PAD, CKM_DES_ECB, CKM_DES_CBC, CKM_AES_XTS # key export with public keys XCP_CPB_WRAP_ASYMM: CKM_RSA_PKCS @@ -48,20 +48,20 @@ # generate asymmetric keypairs XCP_CPB_KEYGEN_ASYMM: CKM_RSA_PKCS_KEY_PAIR_GEN, CKM_RSA_X9_31_KEY_PAIR_GEN, CKM_EC_KEY_PAIR_GEN, CKM_DSA_KEY_PAIR_GEN, CKM_DH_PKCS_KEY_PAIR_GEN -# generate or derive symmetric keys, including DSA parameters -XCP_CPB_KEYGEN_SYMM: CKM_AES_KEY_GEN, CKM_DES2_KEY_GEN, CKM_DES3_KEY_GEN, CKM_DSA_PARAMETER_GEN, CKM_DH_PKCS_PARAMETER_GEN, CKM_PBE_SHA1_DES3_EDE_CBC, CKM_DES_KEY_GEN, CKM_GENERIC_SECRET_KEY_GEN +# generate or derive symmetric keys +XCP_CPB_KEYGEN_SYMM: CKM_AES_KEY_GEN, CKM_DES2_KEY_GEN, CKM_DES3_KEY_GEN, CKM_PBE_SHA1_DES3_EDE_CBC, CKM_DES_KEY_GEN, CKM_GENERIC_SECRET_KEY_GEN, CKM_AES_XTS_KEY_GEN # RSA private-key or key-encrypt use XCP_CPB_ALG_RSA: CKM_RSA_PKCS, CKM_RSA_PKCS_KEY_PAIR_GEN, CKM_RSA_X9_31_KEY_PAIR_GEN, CKM_RSA_PKCS_PSS, CKM_SHA1_RSA_X9_31, CKM_SHA1_RSA_PKCS, CKM_SHA1_RSA_PKCS_PSS, CKM_SHA256_RSA_PKCS, CKM_SHA256_RSA_PKCS_PSS, CKM_SHA224_RSA_PKCS, CKM_SHA224_RSA_PKCS_PSS, CKM_SHA384_RSA_PKCS, CKM_SHA384_RSA_PKCS_PSS, CKM_SHA512_RSA_PKCS, CKM_SHA512_RSA_PKCS_PSS, CKM_RSA_X9_31 # DSA private-key use -XCP_CPB_ALG_DSA: CKM_DSA_PARAMETER_GEN, CKM_DSA_KEY_PAIR_GEN, CKM_DSA, CKM_DSA_SHA1 +XCP_CPB_ALG_DSA: CKM_DSA_KEY_PAIR_GEN, CKM_DSA, CKM_DSA_SHA1 # EC private-key use XCP_CPB_ALG_EC: CKM_EC_KEY_PAIR_GEN, CKM_ECDH1_DERIVE, CKM_ECDSA, CKM_ECDSA_SHA224, CKM_ECDSA_SHA256, CKM_ECDSA_SHA384, CKM_ECDSA_SHA512 # Diffie-Hellman use (private keys) -XCP_CPB_ALG_DH: CKM_ECDH1_DERIVE, CKM_DH_PKCS_PARAMETER_GEN, CKM_DH_PKCS_KEY_PAIR_GEN, CKM_DH_PKCS_DERIVE +XCP_CPB_ALG_DH: CKM_ECDH1_DERIVE, CKM_DH_PKCS_KEY_PAIR_GEN, CKM_DH_PKCS_DERIVE # allow key derivation (symmetric+EC/DH) XCP_CPB_DERIVE: CKM_SHA1_KEY_DERIVATION, CKM_SHA256_KEY_DERIVATION, CKM_SHA384_KEY_DERIVATION, CKM_SHA512_KEY_DERIVATION, CKM_SHA224_KEY_DERIVATION, CKM_ECDH1_DERIVE, CKM_DH_PKCS_DERIVE @@ -73,4 +73,16 @@ XCP_CPB_ALG_NBSI2017: CKM_RSA_PKCS, CKM_SHA1_RSA_PKCS, CKM_SHA224_RSA_PKCS, CKM_SHA256_RSA_PKCS, CKM_SHA384_RSA_PKCS, CKM_SHA512_RSA_PKCS #enable support of Dilithium -XCP_CPB_ALG_PQC: CKM_IBM_DILITHIUM +XCP_CPB_ALG_PQC: CKM_IBM_DILITHIUM, CKM_IBM_KYBER + +# enable BTC-related functionality +XCP_CPB_BTC: CKM_IBM_BTC_DERIVE + +# enable non-ECDSA/non-EdDSA elliptic curve signature algorithms +XCP_CPB_ECDSA_OTHER: CKM_IBM_ECDSA_OTHER + +# allow non-FIPS-approved algs (2021) +XCP_CPB_ALG_NFIPS2021: CKM_RSA_PKCS, CKM_SHA1_RSA_PKCS, CKM_DSA_SHA1, CKM_ECDSA_SHA1, CKM_DES_KEY_GEN, CKM_DES_ECB, CKM_DES_CBC, CKM_DES_CBC_PAD, CKM_DES2_KEY_GEN, CKM_DES3_KEY_GEN, CKM_DES3_ECB, CKM_DES3_CBC, CKM_DES3_MAC, CKM_DES3_MAC_GENERAL, CKM_DES3_CBC_PAD, CKM_DES3_CMAC_GENERAL, CKM_DES3_CMAC, CKM_DES_OFB64, CKM_DES_CFB64, CKM_DES_CFB8, CKM_SHA_1_HMAC, CKM_SHA_1_HMAC_GENERAL, CKM_SHA1_KEY_DERIVATION + +# allow non-FIPS-approved algs (2024) +XCP_CPB_ALG_NFIPS2024: CKM_RSA_PKCS, CKM_SHA1_RSA_PKCS, CKM_DSA_SHA1, CKM_ECDSA_SHA1, CKM_DES_KEY_GEN, CKM_DES_ECB, CKM_DES_CBC, CKM_DES_CBC_PAD, CKM_DES2_KEY_GEN, CKM_DES3_KEY_GEN, CKM_DES3_ECB, CKM_DES3_CBC, CKM_DES3_MAC, CKM_DES3_MAC_GENERAL, CKM_DES3_CBC_PAD, CKM_DES3_CMAC_GENERAL, CKM_DES3_CMAC, CKM_DES_OFB64, CKM_DES_CFB64, CKM_DES_CFB8, CKM_SHA_1_HMAC, CKM_SHA_1_HMAC_GENERAL, CKM_SHA1_KEY_DERIVATION diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11.h opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11.h --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11.h 2023-02-13 09:22:42.000000000 +0100 @@ -1,197 +1,35 @@ /* - * COPYRIGHT (c) International Business Machines Corp. 2020 + * (C) Copyright IBM Corp. 2012, 2022 * * This program is provided under the terms of the Common Public License, * version 1.0 (CPL-1.0). Any use, reproduction or distribution for this * software constitutes recipient's acceptance of CPL-1.0 terms which can be * found in the file LICENSE file or at * https://opensource.org/licenses/cpl1.0.php - */ - -/*---------------------------------------------------------------------- - * This EP11 header file is distributed under the following license - * - * Copyright 2020 IBM Corp. All Rights Reserved - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * - * 1. Redistributions of source code must retain the above copyright notice, - * this list of conditions and the following disclaimer. - * - * 2. Redistributions in binary form must reproduce the above copyright notice, - * this list of conditions and the following disclaimer in the documentation - * and/or other materials provided with the distribution. - * - * 3. Neither the name of the copyright holder nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, - * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR - * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, - * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, - * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; - * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, - * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR - * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF - * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. * *---------------------------------------------------------------------- * EP11 service mail address: EP11SERV@de.ibm.com * * Use this mail address for Bugs and Comments with the EP11 product. - *----------------------------------------------------------------------*/ + *---------------------------------------------------------------------- + */ + #if !defined(XCP_H__) #define XCP_H__ #if !defined(CKR_OK) #include "pkcs11.h" #endif + #if !defined(INT64_MIN) #error "We need 64-bit types, please include before this file." #endif -#if !defined(CKM_SHA224) -#define CKM_SHA224 0x00000255 -#define CKM_SHA224_HMAC 0x00000256 -#define CKM_SHA224_HMAC_GENERAL 0x00000257 -#define CKM_SHA224_RSA_PKCS 0x00000046 -#define CKM_SHA224_RSA_PKCS_PSS 0x00000047 -#define CKM_SHA224_KEY_DERIVATION 0x00000396 -#define CKM_AES_CTR 0x00001086 -#define CKG_MGF1_SHA224 0x00000005 -#endif -#if !defined(CKM_AES_CMAC) -#define CKM_AES_CMAC 0x0000108a -#endif -#if !defined(CKM_DES3_CMAC) -#define CKM_DES3_CMAC 0x00000138 -#endif -#define XCP_MAX_GRPIDX 1024u -#define XCP_MOD_VERSION 2 + +// +// used for internal and external paths/addresses #define MAX_FNAME_CHARS 256 -#define XCPTGTMASK_SET_DOM(mask, domain) \ - mask[((domain)/8)] |= (1 << (7-(domain)%8)) -#define XCPTGTMASK_DOM_IS_SET(mask, domain) \ - (mask[((domain)/8)] & (1 << (7-(domain)%8))) -#define XCPTGTMASK_CLR_DOM(mask, domain) \ - mask[((domain)/8)] &= ~(1 << (7-(domain)%8)) -/* flags that can be set for the target tokens - * - * This flags are domain specific and are therefore called domain flags - * - * start of flags is >16 Bit. Max value for domains is 0xFF. Should be enough - * room for extensions - */ -#define XCP_TGTFL_WCAP 0x10000000 /* Capture wire request in output buffer - * without sending it to the module - */ -#define XCP_TGTFL_WCAP_SQ 0x20000000 /* Size query: Return size of request in - * output buffer length field - */ -#define XCP_TGTFL_SET_SCMD 0x40000000 /* Protected key special command: Set the - * special command flag in the CPRB - * header - */ -#define XCP_TGTFL_API_CHKD 0x80000000 /* supported API version of modules in - * target (group) has been checked - */ -#define XCP_TGTFL_NO_LOCK 0x01000000 /* target token ignores sequential locks - * for target probing - */ -#define XCP_MAXCONNECTIONS 64 /* max value for active connections */ -#define XCP_MAX_PORT 0xffff -typedef struct XCP_ModuleSocket { - char host[ MAX_FNAME_CHARS +1 ]; - uint32_t port; -} *XCP_ModuleSocket_t ; -typedef struct XCP_DomainPerf { - /* perf value of last request per domain - * - * At the moment unused - * */ - unsigned int lastperf[ 256 ]; -} *XCP_DomainPerf_t; -typedef struct XCP_Module { - uint32_t version; /* >0 for supported API versions */ - uint64_t flags; /* see XCP_Module_Flags */ - uint32_t domains; /* max# addressable under this module; - * cached from OS - * - * when callers set domains to 0, the library - * returns the module-claimed domain count. - */ - unsigned char domainmask[ 256 /8 ]; - /* higher domain# through future flags (none - * currently defined) which would add things - * like 'FLAG_256_1023' etc. at the same time, - * we would add domainmask2[] etc. - * corresponding new fields. - * - * new fields would then store mask for - * domains 256+ etc. - * - * domain #0 is bit x80 of 1st byte, - * #255 is bit 0x01 of last byte. - */ - // when a domainmask is supplied, with bits set beyond - // what the module supports, the bitmask is trimmed to - // the supported range, but this is NOT reported as an - // error, unless XCP_MFL_STRICT is also supplied. - // - // without XCP_MFL_STRICT, callers are expected to check - // at least the returned domain count. - /* used only when flags includes XCP_MFL_SOCKET */ - struct XCP_ModuleSocket socket; - /* used when system exposes modules through an - * array of transparent pipes, or similar abstraction - * (such as mainframe AP Queues, or other Linux - * 'device-minor' numbers etc.). Interpretation - * is platform-dependent. - * - * used only when flags includes XCP_MFL_MODULE - */ - uint32_t module_nr; - /* used by systems which associate devices with - * device handles/structs/etc. persistent state. - * opaque pointer, usually a const pointer to - * such aux structs, MAY be stored here. - * - * interpretation is platform-dependent. - * used only when flags includes XCP_MFL_MHANDLE - */ - void *mhandle; - /* diagnostics use only, when XCP_MFL_PERF is set */ - struct XCP_DomainPerf perf; - //----- end of v1 fields ------------------------------------------- - uint32_t api; /* module api version*/ - //----- end of v2 fields ------------------------------------------- -} *XCP_Module_t ; -typedef enum { - XCP_MFL_SOCKET = 1, /* backend is socket-attached */ - XCP_MFL_MODULE = 2, /* backends identified in - array-of-modules */ - XCP_MFL_MHANDLE = 4, /* backends uses 'module handle' field */ - XCP_MFL_PERF = 8, /* performance statistics collected - * for this module, see .perf - */ - XCP_MFL_VIRTUAL = 0x10, /* queried 'target' is a load-balancer, - * other other group. - */ - XCP_MFL_STRICT = 0x20, /* enable aggressive error checking, - * see field descriptions for effect - */ - XCP_MFL_PROBE = 0x40, /* send api query to module, to check if - * target(s) can be used - */ - XCP_MFL_ALW_TGT_ADD = 0x80, /* Allows it to use a target in any - * functional and admin call without - * adding it beforehand with - * m_add_module() - */ - XCP_MFL_MAX = 0xff -} XCP_Module_Flags; + +// Error Values for functions that do not return CK_RV +// general errors #define XCP_OK 0 /* function successful */ #define XCP_EINTERNAL -1 /* host library internal error. @@ -225,6 +63,7 @@ */ #define XCP_EAPI -12 /* incompatible/invalid api */ +// module specific errors #define XCP_MOD_EOBSOLETE -101 /* past feature has been obsoleted, * no longer available. check notes on * future-compatibility. @@ -256,22 +95,36 @@ * This is an error even when the strict * flag is not active */ + /*--------------------------------------------------------------------------*/ #define XCP_COMMON_PUBLIC_H__ -#define XCP_API_VERSION 0x0711 /* major[8] minor[8] */ + + +#define XCP_API_VERSION 0x0810 /* major[8] minor[8] */ #define XCP_API_ORDINAL 0x0004 /* increment this with every major/minor change */ -#define XCP_HOST_API_VER 0x030001 /* major[8] minor[8] fixpack[8] */ -#define XCP_RPM_VERSION XCP_HOST_API_VER /* deprecated */ + +#define XCP_HOST_API_VER 0x040000 /* major[8] minor[8] fixpack[8] */ + /* HSM connection information; not for PKCS11 user consumption */ #define XCP_HSM_AGENT_ID 0x5843 /* ASCII "XC" */ #define XCP_HSM_USERDEF32 0x01234567 + +// protected key requires API ordinal greater or equal to 4 #define XCP_API_ALLOW_PROTKEY 0x0004 + + +// function sub-variants +// 0 means regular request typedef enum { XCP_FNVAR_SIZEQUERY = 1, /* sizequery: databytes[64]->resp.bytes[64] */ XCP_FNVAR_MULTIDATA = 2, /* multi-data request */ XCP_FNVAR_MULTISIZEQ = 3 /* multi-data request, size query */ } XCP_FNVariant_t; + + +// XCP-specific return codes +// #define CKR_IBM_WKID_MISMATCH (CKR_VENDOR_DEFINED +0x10001) #define CKR_IBM_INTERNAL_ERROR (CKR_VENDOR_DEFINED +0x10002) #define CKR_IBM_TRANSPORT_ERROR (CKR_VENDOR_DEFINED +0x10003) @@ -313,26 +166,60 @@ * (which is mapped to standard CKR_FUNCTION_CANCELED) */ #define CKR_IBM_STATIC_POLICY (CKR_VENDOR_DEFINED +0x1000d) + + /* backend not allowed to return requested nr of bytes: */ #define CKR_IBM_TRANSPORT_LIMIT (CKR_VENDOR_DEFINED +0x10010) +// +// use CKR_IBM_TRANSPORT_ERROR for errors introduced between ep11.h and backend +// CKR_IBM_TRANSPORT_LIMIT for errors on return path +// CKR_ARGUMENTS_BAD or specific one for bad data passed through ep11.h + #define CKR_IBM_FCV_NOT_SET (CKR_VENDOR_DEFINED +0x10011) + +// Error returned by check if the performance category has not been set #define CKR_IBM_PERF_CATEGORY_INVALID (CKR_VENDOR_DEFINED +0x10012) + +// API ORDINAL number is unknown or function id is in illegal range #define CKR_IBM_API_MISMATCH (CKR_VENDOR_DEFINED +0x10013) + +// target token is invalid #define CKR_IBM_TARGET_INVALID (CKR_VENDOR_DEFINED +0x10030) + + +#define CKR_IBM_PQC_PARAMS_NOT_SUPPORTED (CKR_VENDOR_DEFINED +0x10031) + + +// Error returned if internal verification of crypto engines fail +#define CKR_IBM_ERROR_STATE (CKR_VENDOR_DEFINED +0x10101) + + /*--- mechanisms ---------------------------------------------------------*/ #define CKM_IBM_SHA3_224 (CKM_VENDOR_DEFINED +0x10001) #define CKM_IBM_SHA3_256 (CKM_VENDOR_DEFINED +0x10002) #define CKM_IBM_SHA3_384 (CKM_VENDOR_DEFINED +0x10003) #define CKM_IBM_SHA3_512 (CKM_VENDOR_DEFINED +0x10004) + #define CKM_IBM_CMAC (CKM_VENDOR_DEFINED +0x10007) +// +// non-SHA-1 ECDSA: no standard mechansims pre-v2.40 #define CKM_IBM_ECDSA_SHA224 (CKM_VENDOR_DEFINED +0x10008) #define CKM_IBM_ECDSA_SHA256 (CKM_VENDOR_DEFINED +0x10009) #define CKM_IBM_ECDSA_SHA384 (CKM_VENDOR_DEFINED +0x1000a) #define CKM_IBM_ECDSA_SHA512 (CKM_VENDOR_DEFINED +0x1000b) + +// EC point multiply #define CKM_IBM_EC_MULTIPLY (CKM_VENDOR_DEFINED +0x1000c) + + +// EAC (machine-readable travel document: passport, DL, ID card PKI) +// +// derive secure messaging, a class of functions #define CKM_IBM_EAC (CKM_VENDOR_DEFINED +0x1000d) #define XCP_EAC_NONCE_MAX_BYTES 64 /* salt/nonce */ #define XCP_EAC_INFO_MAX_BYTES 64 /* other auxiliary data */ +// +// variants within EAC typedef enum { EACV_IBM_KEK_V101 = 1, // secret -> secure msg KEK (EAC v1.01) EACV_IBM_MACK_V101 = 2, // secret -> secure msg MACK (EAC v1.01) @@ -345,48 +232,191 @@ = 5 // blockchain: derive tcert from base EC key // and additive cleartext [potentially insecure] } EAC_Var_t; + +// test access + #define CKM_IBM_TESTCODE (CKM_VENDOR_DEFINED +0x1000e) + + +// SHA-512 derivatives later than PKCS#11 v2.20, SHA-512/256 and SHA-512/224 +// see pkcs11add.h (since v2.40 drafts)(since v2.40 drafts)(since v2.40 drafts)(since v2.40 drafts) +// #define CKM_IBM_SHA512_256 (CKM_VENDOR_DEFINED +0x10012) #define CKM_IBM_SHA512_224 (CKM_VENDOR_DEFINED +0x10013) #define CKM_IBM_SHA512_256_HMAC (CKM_VENDOR_DEFINED +0x10014) #define CKM_IBM_SHA512_224_HMAC (CKM_VENDOR_DEFINED +0x10015) +// + +// curve25519, key agreement #define CKM_IBM_EC_X25519 (CKM_VENDOR_DEFINED +0x1001b) +// +// eddsa/25519 signatures, with SHA-512, no prehashing #define CKM_IBM_ED25519_SHA512 (CKM_VENDOR_DEFINED +0x1001c) +// curve448 ('Goldilocks'), key agreement #define CKM_IBM_EC_X448 (CKM_VENDOR_DEFINED +0x1001e) +// +// ed448 signatures, with SHA-3/XOF, no prehashing #define CKM_IBM_ED448_SHA3 (CKM_VENDOR_DEFINED +0x1001f) + + +// round counts are passed as mechanism parameters #define CKM_IBM_SIPHASH (CKM_VENDOR_DEFINED +0x10021) + + +// these need a strength definition +// XCP_U32_VALUE_BITS/CKA_VALUE_BITS would be sufficient; strength->K/L mapping +// +// umbrella mech for PQC/Crystals variants #define CKM_IBM_DILITHIUM (CKM_VENDOR_DEFINED +0x10023) // ^^^ sign/verify plus keygen only +#define CKM_IBM_KYBER (CKM_VENDOR_DEFINED +0x10024) + // ^^^ en/decrypt, keygen, key transport, and (hybrid) key derivation + +// SHA-3 HMAC variants #define CKM_IBM_SHA3_224_HMAC (CKM_VENDOR_DEFINED +0x10025) #define CKM_IBM_SHA3_256_HMAC (CKM_VENDOR_DEFINED +0x10026) #define CKM_IBM_SHA3_384_HMAC (CKM_VENDOR_DEFINED +0x10027) #define CKM_IBM_SHA3_512_HMAC (CKM_VENDOR_DEFINED +0x10028) + +// curve25519, key agreement (using KEK) #define CKM_IBM_EC_X25519_RAW (CKM_VENDOR_DEFINED +0x10029) + +// curve448 ('Goldilocks'), key agreement (using KEK) #define CKM_IBM_EC_X448_RAW (CKM_VENDOR_DEFINED +0x10030) + +#define CKM_IBM_ECDSA_OTHER (CKM_VENDOR_DEFINED +0x10031) + +typedef enum { + + ECSG_IBM_ECSDSA_S256 = 3, + // [Randomized] Schnorr signatures + // BSI TR03111 ECSDSA + // no prehashing; SHA-256 only + ECSG_IBM_ECSDSA_COMPR_MULTI = 5, + // [Randomized] Schnorr signatures + // BSI TR-03111 @2012, working on + // compressed public key format and + // including signers public key + + ECSG_IBM_MAX = ECSG_IBM_ECSDSA_COMPR_MULTI, +} ECSG_Var_t; + +#define CK_IBM_ECSG_IBM_ECSDSA_S256 ECSG_IBM_ECSDSA_S256 +#define CK_IBM_ECSG_IBM_ECDSA_COMPR_MULTI_S256 ECSG_IBM_ECDSA_COMPR_MULTI_S256 +#define CK_IBM_ECSG_IBM_MAX ECSG_IBM_MAX + + +//--- transport additions -------------------------------------------------- #define CKM_IBM_CLEARKEY_TRANSPORT (CKM_VENDOR_DEFINED +0x20001) +// key+attributes bound format (ignores other attributes) #define CKM_IBM_ATTRIBUTEBOUND_WRAP (CKM_VENDOR_DEFINED +0x20004) +// operations related to key cloning #define CKM_IBM_TRANSPORTKEY (CKM_VENDOR_DEFINED +0x20005) + +// EC/DH equivalents: derive key, then return encrypted under +// KEK supplied as auxiliary data +// (does not resemble regular PKCS11 mechanisms) +// #define CKM_IBM_DH_PKCS_DERIVE_RAW (CKM_VENDOR_DEFINED +0x20006) #define CKM_IBM_ECDH1_DERIVE_RAW (CKM_VENDOR_DEFINED +0x20007) + +// none of these have PKCS11 constants (as of 2018-02) + + +// +// allow direct access to mechanism's wireform +// parameter of this mechanism is used as wire form #define CKM_IBM_WIRETEST (CKM_VENDOR_DEFINED +0x30004) + + +//--- separate infrastructure-related mechs -------------------------------- +// to generate/refill semi-retained keys +// see also CKA_IBM_RETAINKEY +// #define CKM_IBM_RETAINKEY (CKM_VENDOR_DEFINED +0x40001) + + +// IBM protkey data key import mechanism (WrapKey) #define CKM_IBM_CPACF_WRAP (CKM_VENDOR_DEFINED +0x60001) + + +// bitcoin key derivation +#define CKM_IBM_BTC_DERIVE (CKM_VENDOR_DEFINED +0x70001) + /*--- attributes ---------------------------------------------------------*/ + +// object may have rights removed, but not added (subset of modifiability) #define CKA_IBM_RESTRICTABLE (CKA_VENDOR_DEFINED +0x10001) + +// object was created non-MODIFIABLE #define CKA_IBM_NEVER_MODIFIABLE (CKA_VENDOR_DEFINED +0x10002) + +// object is HSM-resident (handle instead of full token) +// has a single parameter, usage count #define CKA_IBM_RETAINKEY (CKA_VENDOR_DEFINED +0x10003) + +// object must be transported with attributes, never separated +// note: incompatible with pure-PKCS#11 un/wrap #define CKA_IBM_ATTRBOUND (CKA_VENDOR_DEFINED +0x10004) + +// symbolic key type in other hierarchies (CK_ULONG) +// XCP stores but ignores it #define CKA_IBM_KEYTYPE (CKA_VENDOR_DEFINED +0x10005) + +// restrictions inherited from other type systems +// XCP stores and partially interprets it #define CKA_IBM_CV (CKA_VENDOR_DEFINED +0x10006) + +// attribute containing MAC key handle, or blob, for authenticated key transport #define CKA_IBM_MACKEY (CKA_VENDOR_DEFINED +0x10007) + +// object may be used as base data of other ops, i.e., hashing or key derivation +// #define CKA_IBM_USE_AS_DATA (CKA_VENDOR_DEFINED +0x10008) + +// DSA/DH parameters as ALGID structure (PKCS#3) #define CKA_IBM_STRUCT_PARAMS (CKA_VENDOR_DEFINED +0x10009) + +// compliance mode, bitfield within 32-bit (CK_ULONG) parameter #define CKA_IBM_STD_COMPLIANCE1 (CKA_VENDOR_DEFINED +0x1000a) + + +// key is extractable only as protected key #define CKA_IBM_PROTKEY_EXTRACTABLE (CKA_VENDOR_DEFINED +0x1000c) + +// key is never extractable as protected key #define CKA_IBM_PROTKEY_NEVER_EXTRACTABLE (CKA_VENDOR_DEFINED +0x1000d) + #define CKA_IBM_PQC_PARAMS (CKA_VENDOR_DEFINED +0x1000e) + +// query or modify login session an object is bound to +#define CKA_IBM_LOGIN_SESSION (CKA_VENDOR_DEFINED +0x1000f) + +// query MAC'd spki from a private key +#define CKA_IBM_MACED_PUBLIC_KEY_INFO (CKA_VENDOR_DEFINED +0x20002) + +// direct access to attributes' wire form +// parameters of this attribute, if it's the only one present, +// inserted verbatim into request package #define CKA_IBM_WIRETEST (CKA_VENDOR_DEFINED +0x20001) + + +// matches the key type constant for clear key Dilithium with ICSF #define CKK_IBM_PQC_DILITHIUM (CKK_VENDOR_DEFINED +0x10023) + +#define CKK_IBM_PQC_KYBER (CKK_VENDOR_DEFINED +0x10024) + + + + + +#define XCP_MOD_ERROR_STATE_OFF 0x00000000 +#define XCP_MOD_ERROR_STATE_MODULE_SELFTEST 0x00000001 +#define XCP_MOD_ERROR_STATE_KEYPAIR_GEN_PCT 0x00000002 +#define XCP_MOD_ERROR_STATE_SYSTEST_CMD 0x00000003 +#define XCP_MOD_ERROR_STATE_TRNG_HEALTH 0x00000004 + + /*---------------------------------------------------------------------------- * sizes related to blobs and host-visible entities * @@ -403,46 +433,99 @@ #define XCP_BLOBCLRATTR_BYTES 8 /* clear blob attr's bytecount */ /* keep in sync with objattr_t */ #define XCP_BLOBCLRMODE_BYTES 8 /* clear blob modefield bytecount */ -#define MOD_WRAP_BLOCKSIZE ((size_t) (128 /8)) /* blob crypt block bytecount */ +#define XCP_WRAP_BLOCKSIZE ((size_t) (128 /8)) /* blob crypt block bytecount */ #define XCP_MACKEY_BYTES (256 /8) /* derived from controlling WK */ -#define XCP_PIN_SALT_BYTES MOD_WRAP_BLOCKSIZE +// +#define XCP_PIN_SALT_BYTES XCP_WRAP_BLOCKSIZE #define XCP_PINBLOB_BYTES \ (XCP_WK_BYTES +XCP_PIN_SALT_BYTES +XCP_HMAC_BYTES) + #define XCP_PBE_TYPE_CLEAR 0 /* clear passphrase */ #define XCP_PBE_TYPE_BLOB 1 /* passphrase as generic secretkey */ #define XCP_PBE_TYPE_MAX (XCP_PBE_TYPE_BLOB) +// #define XCP_PBE_HDR_BYTES 16 /* fixed part of PBE wire struct */ #define XCP_PBE_PWD_MAX_BYTES 1024 #define XCP_PBE_SALT_MAX_BYTES 256 +// currently, these are the largest possible param structs #define XCP_MECH_WIRE_PRM_BYTES ((size_t) 4) /* CK_ULONG(mech) on wire */ #define XCP_MECH_PRM_MAX_BYTES \ (XCP_MECH_WIRE_PRM_BYTES +XCP_PBE_HDR_BYTES \ +XCP_PBE_PWD_MAX_BYTES +XCP_PBE_SALT_MAX_BYTES) + // wire-encoded file header: file ID, start/offset, bytecount // return path fills in fields, plus may supply data slice #define XCP_WIRE_FILEHDR_BYTES ((size_t) (4+4+4)) + +// currently, PBE iteration count limit is global +// the limit may increase, but not decrease, in the future #define XCP_PBE_ITER_MAX (64*1024) + + +// SYS_TEST-only, configuration query size #define XCP_CSP_CONFIG_BYTES 40 + + #define XCP_SESSIONBLOB_SALT_BYTES 16 #define XCP_SESSIONBLOB_BYTES \ (XCP_WK_BYTES +XCP_SESSIONBLOB_SALT_BYTES +XCP_HMAC_BYTES) + #define XCP_SIZEQ_WIRE_BYTES 8 /* wire size of data/response bytecounts */ + + #define XCP_PSS_WIRE_BYTES (4+4+4) /* hash[32] || MGF[32] || salt bytes[32] */ +// +// infer value from mechanism/hash function #define XCP_PSS_DEFAULT_VALUE 0xffffffff + #define XCP_OAEP_MIN_WIRE_BYTES (4+4+4) /* hash[32] || MGF[32] || src[32] */ + #define XCP_OAEP_MAX_SOURCE_BYTES 1024 /* limit encoding parameter length to a sane number of Bytes */ + #define XCP_SHAKE_WIRE_BYTES 4 /* XOF Bytes[32] */ + #define XCP_ECDH1_DERIVE_MIN_WIRE_BYTES (4+4+4) /* kdf[32] || SharedDataLen[32] || PublicDataLen[32] */ + +#define XCP_BTC_MIN_WIRE_BYTES (4+4+4+4) /* type[32] || + childKeyIndex[32] || + chaincode[32] + version[32] */ + +#define XCP_BIP0032_CHAINCODE_BYTES 32 + +#define XCP_BTC_VERSION 1 + +#define XCP_KYBER_KEM_VERSION 0 + +#define XCP_KYBER_KEM_MIN_WIRE_BYTES (4 + 4 + 4 + 4 + 4 + 4) /* version[32] || + kdf[32] || + mode[32] || + cphr[32] || + shrd[32] || + blob [32] */ + +#define XCP_KYBER_RAW_BYTES 32 + + #define XCP_ECDH1_DERIVE_MAX_PUBLIC_BYTES 1024 /* limit public data length to reasonable number of bytes */ +// #define XCP_ECDH1_DERIVE_MAX_SHARED_BYTES 1024 /* limit shared data length to reasonable number of bytes */ +// +// full RK ID (handle) #define XCP_RETAINID_BYTES (XCP_HMAC_BYTES +XCP_HMAC_BYTES) +// +// RK label (name, other human-readable information) #define XCP_RETAINLABEL_BYTES ((size_t) 64) +// +// truncated form #define XCP_RETAINID_SHORT_BYTES 4 + + /*--- infrastructure -----------------------------------------------------*/ typedef enum { CKF_IBM_HW_EXTWNG = 1, // module monitors removal from its slot. @@ -455,33 +538,56 @@ = 0x0200, // module supports domain import // see also related extended capability // (CK_IBM_XCPXQ_DOMIMPORT_VER) + CKF_IBM_HW_PROTKEY_TOLERATION = 0x0400, // module tolerates blob attributes // related to the protected-key capability // see also CKA_IBM_PROTKEY_* description + + CKF_IBM_HW_DUAL_OA = 0x1000, // module supports dual OA certs/signatures + // see CK_IBM_XCPXQ_OA_CAP for more details } XCP_CK_EXTFLAGS_t; + +// these numbers apply to current version, subject to change +// #define XCP_MAX_MODULES 256 /* number of targetable backends */ + #define XCP_SERIALNR_CHARS 8 #define XCP_DOMAIN_INSTANCE_BYTES 4 + #define XCP_WRAPKEY_BYTES 32 /* keep integer blocks of blob cipher */ + #define XCP_SPKISALT_BYTES 8 /* in MACed SPKIs (public key objs) */ #define XCP_DOMAINS 256 /* keep multiple of 8 */ #define XCP_DOMAIN_BYTES 4 /* wire-encoding bytecount */ #define XCP_MAX_ADMINS 8 /* per domain; card has +1 */ #define XCP_MAX_KEYPARTS 20 /* per export/import call */ + #define XCP_MIN_PINBYTES 8 #define XCP_MAX_PINBYTES 16 -#define XCP_CERT_MAX_BYTES ((size_t) 4096) + +// ~arbitrary limit on acceptable admin. certificates +// additional limits, such as transport-bytecount, may restrict further +#define XCP_CERT_MAX_BYTES ((size_t) 12288) /* fits dil certs (8k + meta) */ #define XCP_CERTHASH_BYTES (256/8) /* hash or SKI of public key, or other hash-identified things; SHA-256 */ + #define XCP_ADMCTR_BYTES ((size_t) (128/8)) /* card/domain admin transaction ctrs */ #define XCP_KEYCSUM_BYTES (256/8) /* full size of verification pattern */ + /* maximum coordinate bytecount, NIST P or BP curves */ #define XCP_MAX_EC_COORD_BYTES ((size_t) 66) /* P-521-> 512+9 bits */ +#define XCP_MIN_EC_CURVE_BITS 192 + /* ^^^ increase this when policy moves beyond shorter curves */ #define XCP_MAX_EC_CURVE_BITS 521 + +#define XCP_MAX_DIL_SIGNATURE_BYTES 4668 /* max. length of dil. 8-7 sigs */ +#define XCP_MAX_SINFO_META_BYTES 100 /* signer info framework bytes */ + /* bytecount of raw (generic) keys, not key schedules */ #define MOD_MAX_SYMMKEY_BYTES 256 + #define XCP_FCV_PUBLIC_BYTES ((size_t) 76) /* raw struct without signature */ /**/ /* note: entire signed packet, w/o key info, before Sentry */ @@ -492,86 +598,124 @@ XCP_FCV_EC_BYTES = (76+ 2*66), /* ECDSA/P-521 */ XCP_FCV_MAX_BYTES = XCP_FCV_RSA_BYTES } XCP_FCV_Bytes_t; + + #define PKCS11_CHECKSUM_BYTES ((size_t) 3) #define XCP_KEYBITS_FIELD_BYTES ((size_t) 4) /* trailing big-endian bitcount field after UnwrapKey() checksum */ + +/* card(OA) signature bytecount: SKI-identified SignerInfo, + * Non quantum safe: Must contain space for either: + * - 4096-bit RSA signature, hash OID, encr. OID and SKI + * - EC-P521 signature, hash OID, encr. OID and SKI + */ +#define XCP_RSPSIG_RSA (4096 / 8) +#define XCP_RSPSIG_MAX_BYTES (XCP_MAX_SINFO_META_BYTES + \ + XCP_RSPSIG_RSA) + /* card(OA) signature bytecount: SKI-identified SignerInfo, - 4096-bit RSA signature, with SHA-256 hash */ -#define XCP_RSPSIG_MAX_BYTES (75 +4096/8) + * Quantum safe: Must contain space for: + * - DIL signature, hash OID, encr. OID and SKI + */ +#define XCP_RSPSIG_QS_MAX_BYTES (XCP_MAX_SINFO_META_BYTES + \ + XCP_MAX_DIL_SIGNATURE_BYTES) + /* minimal padding for raw RSA enc/dec/sign/ver/wr/unwr * Used for example in CKM_RSA_PKCS. See RFC 2313 chapter 8 for a complete * description */ #define XCP_RSA_PKCS_MIN_PAD 11 + /*=== audit events =======================================================*/ + #define XCP_LOG_STATE_BYTES (256 /8) /* SHA-256-based hash chain */ + #define XCP_LOG_HEADER_BYTE 0x42 /* event-record header, v0 */ + #define XCP_LOGEV_SPEC (0xffff0000) /* indicates particular events, not generic event types/categories, */ /* if bits in this region are non-zero */ -typedef enum { /* functionality categories: keep within uint16_t range */ - XCP_LOGEV_QUERY = 0, - XCP_LOGEV_FUNCTION = 1, - XCP_LOGEV_ADMFUNCTION = 2, - XCP_LOGEV_STARTUP = 3, - XCP_LOGEV_SHUTDOWN = 4, - XCP_LOGEV_SELFTEST = 5, - XCP_LOGEV_DOM_IMPORT = 6, /* import sec-relevant data to domain */ - XCP_LOGEV_DOM_EXPORT = 7, /* export sec-relevant data from domain */ - XCP_LOGEV_FAILURE = 8, - XCP_LOGEV_GENERATE = 9, - XCP_LOGEV_REMOVE = 10, - XCP_LOGEV_SPECIFIC = 11, /* obtain meaning elsewhere */ - XCP_LOGEV_STATE_IMPORT = 12, /* import to card/multiple domains */ - XCP_LOGEV_STATE_EXPORT = 13, /* export from card/multiple domains */ - /* [after successful export] */ - XCP_LOGEV_IMPORT = 14, /* key/state import (UnwrapKey) */ - /* fields provide more context */ - XCP_LOGEV_EXPORT = 15, /* key/state import (WrapKey) */ - /* fields provide more context */ - /*--- specific events (any including XCP_LOGEV_SPEC) ---------*/ - XCP_LOGSPEV_TRANSACT_ZEROIZE = XCP_LOGEV_SPEC +1, - /* zeroize card by transaction */ - XCP_LOGSPEV_KAT_FAILED = XCP_LOGEV_SPEC +2, - /* algorithm selftest failed */ - XCP_LOGSPEV_KAT_COMPLETED = XCP_LOGEV_SPEC +3, - /* algorithm selftests completed */ - /* redundant; logged only to */ - /* provide specific event */ - XCP_LOGSPEV_EARLY_Q_START = XCP_LOGEV_SPEC +4, - /* subsequent events were found */ - /* in the early-event queue. */ - /* their timestamps are only */ - /* approximate; order is correct */ - XCP_LOGSPEV_EARLY_Q_END = XCP_LOGEV_SPEC +5, - /* early-even queue processing ends. */ - /* subsequent events are through */ - /* regular auditing, with valid */ - /* timestamps and ordering. */ - XCP_LOGSPEV_AUDIT_NEWCHAIN = XCP_LOGEV_SPEC +6, - /* audit state is corrupted; removed. */ - /* generating new instance and start */ - /* new chain as a replacement */ - XCP_LOGSPEV_TIMECHG_BEFORE = XCP_LOGEV_SPEC +7, - /* time change: original time */ - XCP_LOGSPEV_TIMECHG_AFTER = XCP_LOGEV_SPEC +8, - /* time change: updated time */ - XCP_LOGSPEV_MODSTIMPORT_START = XCP_LOGEV_SPEC +9, - /* accepted full-state import */ - /* data structure */ - /* starting update procedure */ - XCP_LOGSPEV_MODSTIMPORT_FAIL = XCP_LOGEV_SPEC +10, - /* rejected import structure */ - /* issued after initial verify; */ - /* indicates some inconsistency */ - /* of import data structures */ - XCP_LOGSPEV_MODSTIMPORT_END = XCP_LOGEV_SPEC +11, - /* completed full-state import */ - XCP_LOGSPEV_MODSTEXPORT_START = XCP_LOGEV_SPEC +12, - /* started full-state export */ - /* see also: XCP_LOGEV_STATE_EXPORT */ - XCP_LOGSPEV_MODSTEXPORT_FAIL = XCP_LOGEV_SPEC +13 - /* full-state export did not complete */ -} XCP_LogEvent_t; + + /* functionality categories: keep within uint16_t range */ +#define XCP_LOGEV_QUERY 0 +#define XCP_LOGEV_FUNCTION 1 +#define XCP_LOGEV_ADMFUNCTION 2 +#define XCP_LOGEV_STARTUP 3 +#define XCP_LOGEV_SHUTDOWN 4 +#define XCP_LOGEV_SELFTEST 5 +#define XCP_LOGEV_DOM_IMPORT 6 /* import sec-relevant data to */ + /* domain */ +#define XCP_LOGEV_DOM_EXPORT 7 /* export sec-relevant data from */ + /* domain */ +#define XCP_LOGEV_FAILURE 8 +#define XCP_LOGEV_GENERATE 9 +#define XCP_LOGEV_REMOVE 10 +#define XCP_LOGEV_SPECIFIC 11 /* obtain meaning elsewhere */ +#define XCP_LOGEV_STATE_IMPORT 12 /* import to card/multiple domains */ +#define XCP_LOGEV_STATE_EXPORT 13 /* export from card/multiple */ + /* domains */ + /* [after successful export] */ +#define XCP_LOGEV_IMPORT 14 /* key/state import (UnwrapKey) */ + /* fields provide more context */ +#define XCP_LOGEV_EXPORT 15 /* key/state import (WrapKey) */ + /* fields provide more context */ + + /*--- specific events (any including XCP_LOGEV_SPEC) ---------*/ + +#define XCP_LOGSPEV_TRANSACT_ZEROIZE (XCP_LOGEV_SPEC +1) + /* zeroize card by transaction */ + +#define XCP_LOGSPEV_KAT_FAILED (XCP_LOGEV_SPEC +2) + /* algorithm selftest failed */ + +#define XCP_LOGSPEV_KAT_COMPLETED (XCP_LOGEV_SPEC +3) + /* algorithm selftests completed */ + /* redundant; logged only to */ + /* provide specific event */ + +#define XCP_LOGSPEV_EARLY_Q_START (XCP_LOGEV_SPEC +4) + /* subsequent events were found */ + /* in the early-event queue. */ + /* their timestamps are only */ + /* approximate; order is correct */ + +#define XCP_LOGSPEV_EARLY_Q_END (XCP_LOGEV_SPEC +5) + /* early-even queue processing ends. */ + /* subsequent events are through */ + /* regular auditing, with valid */ + /* timestamps and ordering. */ + +#define XCP_LOGSPEV_AUDIT_NEWCHAIN (XCP_LOGEV_SPEC +6) + /* audit state is corrupted; removed. */ + /* generating new instance and start */ + /* new chain as a replacement */ + +#define XCP_LOGSPEV_TIMECHG_BEFORE (XCP_LOGEV_SPEC +7) + /* time change: original time */ + +#define XCP_LOGSPEV_TIMECHG_AFTER (XCP_LOGEV_SPEC +8) + /* time change: updated time */ + +#define XCP_LOGSPEV_MODSTIMPORT_START (XCP_LOGEV_SPEC +9) + /* accepted full-state import */ + /* data structure */ + /* starting update procedure */ + +#define XCP_LOGSPEV_MODSTIMPORT_FAIL (XCP_LOGEV_SPEC +10) + /* rejected import structure */ + /* issued after initial verify; */ + /* indicates some inconsistency */ + /* of import data structures */ + +#define XCP_LOGSPEV_MODSTIMPORT_END (XCP_LOGEV_SPEC +11) + /* completed full-state import */ + +#define XCP_LOGSPEV_MODSTEXPORT_START (XCP_LOGEV_SPEC +12) + /* started full-state export */ + /* see also: XCP_LOGEV_STATE_EXPORT */ + +#define XCP_LOGSPEV_MODSTEXPORT_FAIL (XCP_LOGEV_SPEC +13) + + typedef enum { XCP_LOGSYS_AUDIT = 1, /* audit infrastructure itself */ XCP_LOGSYS_CRYPTTEST = 2, /* cryptographic test operations */ @@ -581,38 +725,69 @@ XCP_LOGSYS_WK = 5, /* one wrapping key (WK) */ XCP_LOGSYS_STATE = 6 /* all transportable module state */ } XCP_LogSystem_t; + /* bitmask of audit-event flags (mainly optional fields) */ -typedef enum { - XCP_LOGFL_WK_PRESENT = 0x80000000, - XCP_LOGFL_COMPLIANCE_PRESENT = 0x40000000, /* ...of hosting domain */ - XCP_LOGFL_FINALWK_PRESENT = 0x20000000, - XCP_LOGFL_KEYREC0_PRESENT = 0x10000000, - XCP_LOGFL_KEYREC0_COMPL = 0x08000000, /* key0 compliance */ - XCP_LOGFL_KEYREC1_PRESENT = 0x04000000, - XCP_LOGFL_KEYREC2_PRESENT = 0x02000000, - XCP_LOGFL_FINTIME_PRESENT = 0x01000000, - XCP_LOGFL_SALT0_PRESENT = 0x00800000, - XCP_LOGFL_SALT1_PRESENT = 0x00400000, - XCP_LOGFL_SALT2_PRESENT = 0x00200000, - XCP_LOGFL_REASON_PRESENT = 0x00100000, - XCP_LOGFL_SEQPRF_PRESENT = 0x00080000 -} XCP_LogFlags_t; +#define XCP_LOGFL_WK_PRESENT 0x80000000 +#define XCP_LOGFL_COMPLIANCE_PRESENT 0x40000000 /* ...of hosting domain */ +#define XCP_LOGFL_FINALWK_PRESENT 0x20000000 +#define XCP_LOGFL_KEYREC0_PRESENT 0x10000000 +#define XCP_LOGFL_KEYREC0_COMPL 0x08000000 /* key0 compliance */ +#define XCP_LOGFL_KEYREC1_PRESENT 0x04000000 +#define XCP_LOGFL_KEYREC2_PRESENT 0x02000000 +#define XCP_LOGFL_FINTIME_PRESENT 0x01000000 +#define XCP_LOGFL_SALT0_PRESENT 0x00800000 +#define XCP_LOGFL_SALT1_PRESENT 0x00400000 +#define XCP_LOGFL_SALT2_PRESENT 0x00200000 +#define XCP_LOGFL_REASON_PRESENT 0x00100000 +#define XCP_LOGFL_SEQPRF_PRESENT 0x00080000 + + + +//--- importer PK types ---------------------------------------------------- typedef enum { XCP_IMPRKEY_RSA_2048 = 0, XCP_IMPRKEY_RSA_4096 = 1, - XCP_IMPRKEY_EC_P256 = 2, /* EC, NIST P-256 */ - XCP_IMPRKEY_EC_P521 = 3, /* EC, NIST P-521 */ - XCP_IMPRKEY_EC_BP256r = 4, /* EC, Brainpool BP-256r */ - XCP_IMPRKEY_EC_BP320r = 5, /* EC, Brainpool BP-320r */ - XCP_IMPRKEY_EC_BP512r = 6, /* EC, Brainpool BP-512r */ + XCP_IMPRKEY_EC_P256 = 2, /* EC, NIST P-256 */ + XCP_IMPRKEY_EC_P521 = 3, /* EC, NIST P-521 */ + XCP_IMPRKEY_EC_BP256r = 4, /* EC, Brainpool BP-256r */ + XCP_IMPRKEY_EC_BP320r = 5, /* EC, Brainpool BP-320r */ + XCP_IMPRKEY_EC_BP512r = 6, /* EC, Brainpool BP-512r */ XCP_IMPRKEY_RSA_3072 = 7, - XCP_IMPRKEY_MAX = XCP_IMPRKEY_RSA_3072 + XCP_IMPRKEY_EC_P521_TKE = 8, /* EC, NIST P-521 (TKE propr. sign.) */ + XCP_IMPRKEY_MAX = XCP_IMPRKEY_EC_P521_TKE } XCP_IMPRKEY_t; + + +//--- OA key types ---------------------------------------------------- +typedef enum { + XCP_OAKEY_RSA_4096 = 1, /* RSA 4096 bit */ + XCP_OAKEY_ECC_P521 = 2, /* ECC NIST P-521 */ + XCP_OAKEY_DIL_87R2 = 3, /* DIL 8-7 R2 */ + XCP_OAKEY_MAX = XCP_OAKEY_DIL_87R2 +} XCP_OAKEY_t; + + + +//--- retained key structures --------------------------- +// initial loading: +// NULL rkData means no refills; invalid with 0 credits +// +// serialized as: +// nothing if structure is missing (i.e., no restrictions) +// +// credits [be32] if structure is present +// rkdata [var ] +// typedef struct CK_RETAINEDKEY_PARAMS { CK_ULONG credits; CK_VOID_PTR rkData; CK_ULONG rkdLen; } CK_RETAINEDKEY_PARAMS; + + + + +//--- operation categories (perf. measurement) ----------------------------- typedef enum { XCP_OPCAT_ASYMM_SLOW = 1, XCP_OPCAT_ASYMM_FAST = 2, @@ -621,6 +796,10 @@ XCP_OPCAT_ASYMM_GEN = 5, XCP_OPCAT_ASYMM_MAX = XCP_OPCAT_ASYMM_GEN } XCP_OPCAT_t; +// + + +//--- query sub-types ------------------------------------------------------ typedef enum { CK_IBM_XCPQ_API = 0, /* API and build identifier */ CK_IBM_XCPQ_MODULE = 1, /* module-level information */ @@ -630,7 +809,7 @@ CK_IBM_XCPQ_EXT_CAPS = 5, /* extended capabilities, count */ CK_IBM_XCPQ_EXT_CAPLIST = 6, /* extended capabilities, list */ CK_IBM_XCPQ_AUDITLOG = 8, /* audit record or records */ - CK_IBM_XCPQ_DESCRTEXT = 9, /* human-readable text/tokens */ + /* 9 not used ----------------- */ CK_IBM_XCPQ_EC_CURVES = 10, /* supported elliptic curves, */ /* individual curves, bitmask */ /* see: XCP_ECcurve_t */ @@ -644,41 +823,75 @@ /* control points which may */ /* never be enabled due to */ /* policy-minimum restrictions. */ - CK_IBM_XCPQ_MAX = CK_IBM_XCPQ_CP_BLACKLIST + + CK_IBM_XCPQ_PQC_STRENGTHS + = 14, /* supported quantum safe levels*/ + /* of strength */ + /* see: XCP_PQCStrength_t */ + + CK_IBM_XCPQ_MAX = CK_IBM_XCPQ_PQC_STRENGTHS } CK_IBM_XCPQUERY_t; -#define CK_IBM_XCP_HOSTQ_IDX 0xff000000 /* host-only queries index, min. */ + +//--- module sub-query sub-types -------------------------------------------- typedef enum { - CK_IBM_XCPHQ_COUNT = 0xff000000, /* number of host-query indexes */ - /* including this type itself */ - CK_IBM_XCPHQ_VERSION = 0xff000001, /* host-specific package version */ - /* such as packaging library ID */ - CK_IBM_XCPHQ_VERSION_HASH = 0xff000002, - /* assumed-unique identifier of */ - /* host code, such as version- */ - /* identifying cryptographic hash */ - /* (library signature field...) */ - CK_IBM_XCPHQ_DIAGS = 0xff000003, /* host code diagnostic level */ - /* 0 if non-diagnostics host code */ - CK_IBM_XCPHQ_HVERSION = 0xff000004, /* human-readable host version */ - /* identification (recommended: */ - /* UTF-8 string) */ - CK_IBM_XCPHQ_TGT_MODE = 0xff000005, /* host targeting modes */ - /* returns supported target modes */ - /* as bitmask */ - /* if not available only compat */ - /* target mode is in use */ - /* See CK_IBM_XCPHQ_TGT_MODES_t */ - CK_IBM_XCPHQ_ECDH_DERPRM = 0xff000006, - /* ECDH DeriveKey parameter usage */ - /* is being enforced with hostlib */ - /* version */ - /**/ - CK__IBM_XCPHQ_MAX = CK_IBM_XCPHQ_TGT_MODE -} CK_IBM_XCPHQUERY_t; + CK_IBM_XCPMSQ_DEFAULT = 0, /* zero indicates no sub-query */ + CK_IBM_XCPMSQ_DESCRTEXT = 1, /* human-readable text/tokens */ + CK_IBM_XCPMSQ_FNLIST = 2, /* supported function id bitmask*/ + CK_IBM_XCPMSQ_FNS = 3, /* count of fn ids */ + CK_IBM_XCPMSQ_MOD_V1 = 4, /* add version one fields to */ + /* module query */ + CK_IBM_XCPMSQ_ATTRLIST = 5, /* supported administrative */ + /* attributes bitmask */ + CK_IBM_XCPMSQ_ATTRS = 6, /* number of supported */ + /* administrative attributes */ + CK_IBM_XCPMSQ_MOD_V2 = 7, /* add version two fields to */ + /* module query */ + CK_IBM_XCPMSQ_MAX = CK_IBM_XCPMSQ_MOD_V2 +} CK_IBM_XCPMSUBQUERY_t; + +// byte sizes of queries which are not represented as structures +#define XCP_MSQ_FNLIST_SIZE 16 +#define XCP_XCPMSQ_FNS_SIZE 1 + + + +#define CK_IBM_XCP_HOSTQ_IDX 0xff000000 /* host-only queries index, min. */ + +#define CK_IBM_XCPHQ_COUNT 0xff000000 /* number of host-query indexes */ + /* including this type itself */ +#define CK_IBM_XCPHQ_VERSION 0xff000001 /* host-specific package version */ + /* such as packaging library ID */ +#define CK_IBM_XCPHQ_VERSION_HASH 0xff000002 + /* assumed-unique identifier of */ + /* host code, such as version- */ + /* identifying cryptographic hash*/ + /* (library signature field...) */ +#define CK_IBM_XCPHQ_DIAGS 0xff000003 /* host code diagnostic level */ + /* 0 if non-diagnostics host code*/ +#define CK_IBM_XCPHQ_HVERSION 0xff000004 /* human-readable host version */ + /* identification (recommended: */ + /* UTF-8 string) */ +#define CK_IBM_XCPHQ_TGT_MODE 0xff000005 /* host targeting modes */ + /* returns supported target modes*/ + /* as bitmask */ + /* if not available only compat */ + /* target mode is in use */ + /* See CK_IBM_XCPHQ_TGT_MODES_t */ +#define CK_IBM_XCPHQ_ECDH_DERPRM 0xff000006 + /* ECDH DeriveKey parameter usage*/ + /* is being enforced with hostlib*/ + /* version */ + /**/ + +#define CK__IBM_XCPHQ_MAX CK_IBM_XCPHQ_TGT_MODE + + typedef enum { CK_IBM_XCPHQ_TGT_MODES_TGTGRP = 1, /* target groups are supported */ CK_IBM_XCPHQ_TGT_MODES_MAX = CK_IBM_XCPHQ_TGT_MODES_TGTGRP } CK_IBM_XCPHQ_TGT_MODES_t; + + typedef enum { CK_IBM_XCPXQ_AUDIT_EV_BYTES = 2, /* largest audit event, bytecount */ CK_IBM_XCPXQ_AUDIT_ENTRIES = 3, /* max. size of event history */ @@ -691,9 +904,9 @@ /* sub-fields in multi-data */ /* requests. 0 if not supported, */ /* all-1's if no predefined limit. */ - CK_IBM_XCPXQ_DOMIMPORT_VER = 7, /* 1-based revision of domain- */ - /* import capability. 0 if feature */ - /* is not supported */ + CK_IBM_XCPXQ_IMPEXP_CAPS = 7, /* capability for WK and state */ + /* export / import. See 8.7.1.1.1 */ + /* for more info */ CK_IBM_XCPXQ_CERT_MAXBYTES = 8, /* bytecount of largest accepted */ /* administrative certificate, if */ /* there is an upper limit. 0 if */ @@ -701,26 +914,40 @@ /* any specific limit of its own. */ CK_IBM_XCPXQ_MOD_COUNTERS = 9, /* number of module-internal dev */ /* counters supported, 0 if none */ + + CK_IBM_XCPXQ_MAX_SESSIONS = 12, CK_IBM_XCPXQ_AVAIL_SESSIONS = 13, /* maximum, currently available */ /* number of backend sessions */ - CK_IBM_XCPXQ_MAXIDX = CK_IBM_XCPXQ_AVAIL_SESSIONS + CK_IBM_XCPXQ_BTC_CAP = 14, /* bit field for bitcoin related */ + /* additions */ + + CK_IBM_XCPXQ_ECDSA_OTHER = 15, /* bitmask of supported, other EC + signing mechanisms */ + CK_IBM_XCPXQ_OA_CAP = 16, /* bitmask of supported outbound + authority signing mechanisms */ + + CK_IBM_XCPXQ_MAXIDX = CK_IBM_XCPXQ_OA_CAP, } CK_IBM_XCPEXTCAP_t; -typedef enum { - CK_IBM_DOM_ADMIND = 1, /* administrators present */ - CK_IBM_DOM_CURR_WK = 2, /* domain has current WK */ - CK_IBM_DOM_NEXT_WK = 4, /* domain has pending/next WK */ - CK_IBM_DOM_COMMITTED_NWK = 8, /* next WK is active(committed) */ - CK_IBM_DOM_IMPRINTED = 0x10, /* has left imprint mode */ - CK_IBM_DOM_IMPRINTS = 0x80000000, /* enforces imprint mode */ - CK_IBM_DOM_PROTKEY_ALLOW = 0x20 /* policies allow protected key */ -} CK_IBM_DOMAINQ_t; + + +#define CK_IBM_DOM_ADMIND 1 /* administrators present */ +#define CK_IBM_DOM_CURR_WK 2 /* domain has current WK */ +#define CK_IBM_DOM_NEXT_WK 4 /* domain has pending/next WK */ +#define CK_IBM_DOM_COMMITTED_NWK 8 /* next WK is active(committed) */ +#define CK_IBM_DOM_IMPRINTED 0x10 /* has left imprint mode */ +#define CK_IBM_DOM_IMPRINTS 0x80000000 /* enforces imprint mode */ +#define CK_IBM_DOM_PROTKEY_ALLOW 0x20 /* policies allow protected key */ +// +// note: CK_IBM_DOM_IMPRINTS will go away + #define CK_IBM_DOM_ACTIVE \ (CK_IBM_DOM_ADMIND | \ CK_IBM_DOM_CURR_WK | \ CK_IBM_DOM_NEXT_WK | \ CK_IBM_DOM_COMMITTED_NWK | \ CK_IBM_DOM_IMPRINTED) + typedef enum { CK_IBM_ECCURVE_NIST = 1, /* NIST P-curves P-192 to P-521 */ CK_IBM_ECCURVE_BPOOL = 2, /* Brainpool curves, regular+twisted */ @@ -731,44 +958,124 @@ /* are not reported separately */ CK_IBM_ECCURVE_ED448 = 0x20, /* ed448 (Goldilocks) Edwards curve */ } CK_IBM_ECCURVEQ_t; + + typedef struct CK_IBM_XCPAPI_INFO { CK_ULONG firmwareApi; CK_ULONG firmwareConfig; /* truncated firmware hash */ } CK_IBM_XCPAPI_INFO; + typedef CK_IBM_XCPAPI_INFO CK_PTR CK_IBM_XCPAPI_INFO_PTR; + +#define CK_IBM_XCP_INFO_MEMBERS_V0 \ + CK_ULONG firmwareApi; /* API ordinal number */ \ + /* major+minor pairs */ \ + CK_ULONG firmwareId; /* truncated firmwareConfig */ \ + CK_VERSION firmwareVersion; /* xcp only, matches xcpConfig below */ \ + CK_VERSION cspVersion; \ + /* hashes, possibly truncated */ \ + CK_BYTE firmwareConfig[ 32 ]; \ + CK_BYTE xcpConfig[ 32 ]; \ + CK_BYTE cspConfig[ 32 ]; \ + CK_CHAR serialNumber[ 16 ]; /* device || instance */ \ + CK_CHAR utcTime[ 16 ]; \ + CK_ULONG opMode2; /* currently, reserved 0 */ \ + CK_ULONG opMode1; /* operational mode, card-level */ \ + CK_FLAGS flags; /* PKCS#11 capabilities */ \ + CK_FLAGS extflags; /* non-PKCS#11 capabilities */ \ + CK_ULONG domains; \ + CK_ULONG symmStateBytes; \ + CK_ULONG digestStateBytes; \ + CK_ULONG pinBlockBytes; \ + CK_ULONG symmKeyBytes; \ + CK_ULONG spkiBytes; \ + CK_ULONG prvkeyBytes; \ + CK_ULONG maxPayloadBytes; \ + CK_ULONG cpProfileBytes; \ + CK_ULONG controlPoints; + +#define CK_IBM_XCP_DESCINFO_MEMBER \ + CK_CHAR manufacturerID[ 32 ]; \ + CK_CHAR model[ 16 ]; + +#define CK_IBM_XCP_ADMATTRLIST_MEMBER \ + CK_BYTE perm_modes[ 8 ]; \ + CK_BYTE infra_modes[ 8 ]; \ + CK_BYTE comp_modes[ 8 ]; + +#define CK_IBM_XCP_ADMATTRCOUNT_MEMBER \ + CK_BYTE perm_count; \ + CK_BYTE infra_count; \ + CK_BYTE comp_count; + +#define CK_IBM_XCP_ADMATTRLIST_MEMBER_V2 \ + CK_BYTE perm_ext01_modes[ 8 ]; + +#define CK_IBM_XCP_ADMATTRCOUNT_MEMBER_V2 \ + CK_BYTE perm_ext01_count; + +// see chapter 5.1.1. in the wire spec typedef struct CK_IBM_XCP_INFO { - CK_ULONG firmwareApi; /* API ordinal number */ - /* major+minor pairs */ - CK_ULONG firmwareId; /* truncated firmwareConfig */ - CK_VERSION firmwareVersion; /* xcp only, matches xcpConfig below */ - CK_VERSION cspVersion; - /* hashes, possibly truncated */ - CK_BYTE firmwareConfig[ 32 ]; - CK_BYTE xcpConfig [ 32 ]; - CK_BYTE cspConfig [ 32 ]; - CK_CHAR serialNumber[ 16 ]; /* device || instance */ - CK_CHAR utcTime [ 16 ]; - CK_ULONG opMode2; /* currently, reserved 0 */ - CK_ULONG opMode1; /* operational mode, card-level */ - CK_FLAGS flags; /* PKCS#11 capabilities */ - CK_FLAGS extflags; /* non-PKCS#11 capabilities */ - CK_ULONG domains; - CK_ULONG symmStateBytes; - CK_ULONG digestStateBytes; - CK_ULONG pinBlockBytes; - CK_ULONG symmKeyBytes; - CK_ULONG spkiBytes; - CK_ULONG prvkeyBytes; - CK_ULONG maxPayloadBytes; - CK_ULONG cpProfileBytes; - CK_ULONG controlPoints; + CK_IBM_XCP_INFO_MEMBERS_V0 } CK_IBM_XCP_INFO; +// +// see chapter 5.1.1. in the wire spec +typedef struct CK_IBM_XCP_INFO_V1 { + CK_IBM_XCP_INFO_MEMBERS_V0 + CK_IBM_XCP_DESCINFO_MEMBER + CK_BYTE fnid_mask[ 16 ]; + CK_BYTE fnid_count; + CK_IBM_XCP_ADMATTRLIST_MEMBER + CK_IBM_XCP_ADMATTRCOUNT_MEMBER +} CK_IBM_XCP_INFO_V1; +// +// see chapter 5.1.1. in the wire spec +typedef struct CK_IBM_XCP_INFO_V2 { + CK_IBM_XCP_INFO_MEMBERS_V0 + CK_IBM_XCP_DESCINFO_MEMBER + CK_BYTE fnid_mask[ 16 ]; + CK_BYTE fnid_count; + CK_IBM_XCP_ADMATTRLIST_MEMBER + CK_IBM_XCP_ADMATTRCOUNT_MEMBER + CK_IBM_XCP_ADMATTRLIST_MEMBER_V2 + CK_IBM_XCP_ADMATTRCOUNT_MEMBER_V2 +} CK_IBM_XCP_INFO_V2; +// +// see chapter 5.1.1.1. in the wire spec +typedef struct CK_IBM_XCP_DESCINFO { + CK_IBM_XCP_DESCINFO_MEMBER +} CK_IBM_XCP_DESCINFO; +// +// see chapter 5.1.1.3. in the wire spec +typedef struct CK_IBM_XCP_ATTRLIST { + CK_IBM_XCP_ADMATTRLIST_MEMBER + CK_IBM_XCP_ADMATTRLIST_MEMBER_V2 +} CK_IBM_XCP_ATTRLIST; +// +// see chapter 5.1.1.3. in the wire spec +typedef struct CK_IBM_XCP_ATTRCOUNT { + CK_IBM_XCP_ADMATTRCOUNT_MEMBER + CK_IBM_XCP_ADMATTRCOUNT_MEMBER_V2 +} CK_IBM_XCP_ATTRCOUNT; + /**/ #define CK_IBM_XCP_INFO_INIT0 \ { 0,0, {0,0,},{0,0,}, {0,},{0,},{0,}, {0,},{0,}, \ 0,0, 0,0, 0,0,0,0,0,0,0, 0,0,0, } -typedef CK_IBM_XCP_INFO CK_PTR CK_IBM_XCP_INFO_PTR; -typedef CK_IBM_XCP_INFO CK_IBM_EP11_INFO; + +#define CK_IBM_XCP_INFO_V2_INIT0 \ + { 0,0, {0,0,},{0,0,}, {0,},{0,},{0,}, {0,},{0,}, \ + 0,0, 0,0, 0,0,0,0,0,0,0, 0,0,0, \ + {0}, {0}, {0}, 0, {0}, {0}, {0}, 0, 0, 0, \ + {0}, 0} + +typedef CK_IBM_XCP_INFO CK_PTR CK_IBM_XCP_INFO_PTR; +typedef CK_IBM_XCP_INFO_V1 CK_PTR CK_IBM_XCP_INFO_V1_PTR; +typedef CK_IBM_XCP_INFO_V2 CK_PTR CK_IBM_XCP_INFO_V2_PTR; +typedef CK_IBM_XCP_DESCINFO CK_PTR CK_IBM_XCP_DESCINFO_PTR; +typedef CK_IBM_XCP_ATTRLIST CK_PTR CK_IBM_XCP_ATTRLIST_PTR; +typedef CK_IBM_XCP_ATTRCOUNT CK_PTR CK_IBM_XCP_ATTRCOUNT_PTR; + typedef struct CK_IBM_DOMAIN_INFO { CK_ULONG domain; CK_BYTE wk[ XCP_KEYCSUM_BYTES ]; @@ -778,7 +1085,64 @@ } CK_IBM_DOMAIN_INFO; /**/ #define CK_IBM_DOMAIN_INFO_INIT0 { 0, { 0, }, { 0, }, 0, { 0, } } + + typedef CK_IBM_DOMAIN_INFO CK_PTR CK_IBM_DOMAIN_INFO_PTR; + + +//--- BTC mechparams -------------------------------------------------- +typedef struct CK_IBM_BTC_DERIVE_PARAMS { + CK_ULONG type; + CK_ULONG childKeyIndex; + CK_BYTE_PTR pChainCode; + CK_ULONG ulChainCodeLen; + CK_ULONG version; +} CK_IBM_BTC_DERIVE_PARAMS; + +typedef CK_IBM_BTC_DERIVE_PARAMS CK_PTR CK_IBM_BTC_DERIVE_PARAMS_PTR; + +// key index flag; hardened, i.e., keys cannot be used for pub2pub derivation +#define CK_IBM_BIP0032_HARDENED (0x80000000) + +// sub-variants of BIP-0032 key derivation +typedef enum { + CK_IBM_BIP0032_PRV2PRV = 1, + CK_IBM_BIP0032_PRV2PUB = 2, + CK_IBM_BIP0032_PUB2PUB = 3, + CK_IBM_BIP0032_MASTERK = 4, + CK_IBM_SLIP0010_PRV2PRV = 5, + CK_IBM_SLIP0010_PRV2PUB = 6, + CK_IBM_SLIP0010_PUB2PUB = 7, + CK_IBM_SLIP0010_MASTERK = 8, +} CK_IBM_BTC_t; + + +typedef enum { + XCP_KEM_ENCAPSULATE = 1, + XCP_KEM_DECAPSULATE = 2, +} XCP_KEM_t; + +typedef CK_ULONG CK_IBM_KEM_MODE; + +#define CK_IBM_KEM_ENCAPSULATE XCP_KEM_ENCAPSULATE +#define CK_IBM_KEM_DECAPSULATE XCP_KEM_DECAPSULATE + +typedef struct XCP_KYBER_KEM_PARAMS { + CK_ULONG version; + CK_IBM_KEM_MODE mode; + CK_ULONG kdf; + CK_BBOOL prepend; + CK_BYTE *pCipher; + CK_ULONG ulCipherLen; + CK_BYTE *pSharedData; + CK_ULONG ulSharedDataLen; + CK_BYTE *pBlob; + CK_ULONG ulBlobLen; +} XCP_KYBER_KEM_PARAMS_t; + + +//--- attribute constants -------------------------------------------------- +// typedef enum { XCP_BLOB_EXTRACTABLE = 1, // May be encrypted by other keys. @@ -810,6 +1174,7 @@ // to other processing as data, // such as hashed, or deriving // keys from them. + XCP_BLOB_SIGN = 0x0100, // may generate signatures XCP_BLOB_SIGN_RECOVER = 0x0200, @@ -826,6 +1191,7 @@ XCP_BLOB_VERIFY_RECOVER = 0x010000, // may verify signatures and recover // signed messages + XCP_BLOB_TRUSTED = 0x020000, // PKCS11 CKA_TRUSTED key XCP_BLOB_WRAP_W_TRUSTED = 0x040000, // needs CKA_TRUSTED KEK // note: _TRUSTED enforcement does not @@ -845,39 +1211,51 @@ // modified. XCP_BLOB_BIT_MAX = XCP_BLOB_PROTKEY_NEVER_EXTRACTABLE } XCP_Attr_t; + + +//--- control points ------------------------------------------------------- #define XCP_CPID_BYTES 8 /* bytecount in CP profiles */ /* if backend supports them */ + #define XCP_CPBLOCK_BITS 128 /* handle CPs in this granularity */ /* CP sets get padded to multiple */ + typedef enum { - XCP_CPB_ADD_CPBS = 0, // allow addition (activation) of CP bits - XCP_CPB_DELETE_CPBS = 1, // disable activating further control points + XCP_CPB_ADD_CPBS = 0, // allow activation of CP bits + XCP_CPB_DELETE_CPBS = 1, // allow deactivation of CP bits // (remove both ADD_CPBs and DELETE_CPBs // to make unit read-only) + XCP_CPB_SIGN_ASYMM = 2, // sign with private keys XCP_CPB_SIGN_SYMM = 3, // sign with HMAC or CMAC XCP_CPB_SIGVERIFY_SYMM = 4, // verify with HMAC or CMAC. // No asymmetric counterpart: one // may not restrict use of public keys. + XCP_CPB_ENCRYPT_SYMM = 5, // encrypt with symmetric keys. // No asymmetric counterpart: one // may not restrict use of public keys. + XCP_CPB_DECRYPT_ASYMM = 6, // decrypt with private keys XCP_CPB_DECRYPT_SYMM = 7, // decrypt with symmetric keys + XCP_CPB_WRAP_ASYMM = 8, // key export with public keys XCP_CPB_WRAP_SYMM = 9, // key export with symmetric keys XCP_CPB_UNWRAP_ASYMM = 10, // key import with private keys XCP_CPB_UNWRAP_SYMM = 11, // key import with symmetric keys + XCP_CPB_KEYGEN_ASYMM = 12, // generate asymmetric keypairs // (fn:GenerateKeyPair) XCP_CPB_KEYGEN_SYMM = 13, // generate or derive symmetric keys // including DSA or DH parameters + XCP_CPB_RETAINKEYS = 14, // allow backend to save semi-retained keys XCP_CPB_SKIP_KEYTESTS = 15, // disable selftests on new asymmetric keys XCP_CPB_NON_ATTRBOUND = 16, // allow keywrap without attribute-binding XCP_CPB_MODIFY_OBJECTS = 17, // allow changes to objects (Booleans only) XCP_CPB_RNG_SEED = 18, // allow mixing external seed to RNG // backend may restrict further + XCP_CPB_ALG_RAW_RSA = 19, // allow RSA private-key use without padding // (highly discouraged) XCP_CPB_ALG_NFIPS2009 = 20, // allow non-FIPS-approved algs (as of 2009) @@ -886,6 +1264,7 @@ // including non-BSI keysizes XCP_CPB_KEYSZ_HMAC_ANY = 22, // don't enforce minimum keysize on HMAC // (allows keys shorter than half of digest) + XCP_CPB_KEYSZ_BELOW80BIT = 23, // allow algorithms below 80-bit strength XCP_CPB_KEYSZ_80BIT = 24, // allow 80 to 111-bit algorithms XCP_CPB_KEYSZ_112BIT = 25, // allow 112 to 127-bit algorithms @@ -893,17 +1272,21 @@ XCP_CPB_KEYSZ_192BIT = 27, // allow 192 to 255-bit algorithms XCP_CPB_KEYSZ_256BIT = 28, // allow 256-bit algorithms XCP_CPB_KEYSZ_RSA65536 = 29, // allow RSA public exponents below 0x10001 + XCP_CPB_ALG_RSA = 30, // RSA private-key or key-encrypt use XCP_CPB_ALG_DSA = 31, // DSA private-key use XCP_CPB_ALG_EC = 32, // EC private-key use (see CP on curves) XCP_CPB_ALG_EC_BPOOLCRV = 33, // Brainpool (E.U.) EC curves XCP_CPB_ALG_EC_NISTCRV = 34, // NIST/SECG EC curves + XCP_CPB_ALG_NFIPS2011 = 35, // allow non-FIPS-approved algs (as of 2011) // including non-FIPS keysizes XCP_CPB_ALG_NBSI2011 = 36, // allow non-BSI algorithms (as of 2011) // including non-BSI keysizes + XCP_CPB_USER_SET_TRUSTED = 37, // allow non-admin set TRUSTED on blob/SPKI XCP_CPB_ALG_SKIP_CROSSCHK = 38, // do not double-check sign/decrypt ops + XCP_CPB_WRAP_CRYPT_KEYS = 39, // allow keys which can en/decrypt data // and also un/wrap other keys // (applies to both generation and use) @@ -913,6 +1296,7 @@ XCP_CPB_WRAP_SIGN_KEYS = 41, // allow keys which can un/wrap data // and also sign/verify // (applies to both generation and use) + XCP_CPB_USER_SET_ATTRBOUND = 42, // allow non-administrators to // mark public key objects ATTRBOUND XCP_CPB_ALLOW_PASSPHRASE = 43, // allow host to pass passprases, such as @@ -923,25 +1307,190 @@ // MAC and attributes XCP_CPB_ALG_DH = 46, // Diffie-Hellman use (private keys) XCP_CPB_DERIVE = 47, // allow key derivation (symmetric+EC/DH) + + XCP_CPB_ALLOW_NONSESSION = 48, // allow use of blobs without sessions + // i.e., key/session state not bound + // to Login/Logout-controlled state XCP_CPB_ALG_EC_25519 = 55, // enable support of curve25519, // c448 and related algorithms // incl. EdDSA (ed25519 and ed448) + XCP_CPB_ALG_EC_SECGCRV = 60, // Prime-field SECG EC curves excluding + // those shared with NIST P-curves XCP_CPB_ALG_NBSI2017 = 61, // allow non-BSI algorithms (as of 2017) // including non-BSI keysizes // (fn:Sign/RSA) XCP_CPB_CPACF_PK = 64, // support data key generation and import // for protected key + XCP_CPB_ALG_PQC = 65, // support for PQ algorithms (top CPB) - XCP_CPBITS_MAX = 65 + + XCP_CPB_BTC = 66, // enable BTC-related functionality + // including blockchain, altcoins, and + // digital assets + + XCP_CPB_ECDSA_OTHER = 67, // enable non-ECDSA/non-EdDSA elliptic + // curve signature algorithms + XCP_CPB_ALG_NFIPS2021 = 68, // allow non-FIPS-approved algs (2021) + + XCP_CPB_ALG_NFIPS2024 = 69, // allow non-FIPS-approved algs (2024) + + XCP_CPB_COMPAT_LEGACY_SHA3 = 70, // allow fall-back to non-standard + // SHA3 defaults + XCP_CPB_DSA_PARAMETER_GEN = 71, // allow DSA/PQG parameter generation + XCP_CPB_DERIVE_NON_AB_KEYS = 72, // allow the derivation of a non-AB or raw + // from an AB key. Only relevant if + // XCP_CPB_NON_ATTRBOUND + XCP_CPBITS_MAX = XCP_CPB_DERIVE_NON_AB_KEYS + // marks last used CPB } XCP_CPbit_t; + + +// rounded CP count, multiple of XCP_CPBLOCK_BITS +// integer bytes, by construction (CPBLOCK_BITS is) +// #define XCP_CPCOUNT \ (((XCP_CPBITS_MAX +XCP_CPBLOCK_BITS-1) /XCP_CPBLOCK_BITS) *XCP_CPBLOCK_BITS) + #define XCP_CP_BYTES (XCP_CPCOUNT /8) /* full blocks, incl. unused bits */ + #define XCP_CPB__INVERT (XCP_CPCOUNT-1) /* reserve MS CP bit for negation */ + + /*--- CP checks --------------------*/ +// +// XCP_CPB_ADD_CPBS +// - SetAttribute() +// XCP_CPB_DELETE_CPBS +// - SetAttribute() -- if attempting to set a previously unset attribute +// XCP_CPB_SIGN_ASYMM +// - SignSingle() -- private key blobs +// - SignInit() -- private key blobs +// XCP_CPB_SIGN_SYMM +// - SignSingle() -- symmetric blobs +// - SignInit() -- symmetric blobs +// XCP_CPB_SIGVERIFY_SYMM +// - VerifySingle() -- symmetric blobs +// - VerifyInit() -- symmetric blobs +// XCP_CPB_ENCRYPT_SYMM +// - EncryptSingle() -- symmetric blobs +// - EncryptInit() -- symmetric blobs +// XCP_CPB_DECRYPT_ASYMM +// - DecryptSingle() -- private key blobs +// - DecryptInit() -- private key blobs +// XCP_CPB_DECRYPT_SYMM +// - DecryptSingle() -- symmetric blobs +// - DecryptInit() -- symmetric blobs +// XCP_CPB_WRAP_ASYMM +// - WrapKey() -- SPKIs +// XCP_CPB_WRAP_SYMM +// - WrapKey() -- symmetric blobs +// XCP_CPB_UNWRAP_ASYMM +// - UnwrapKey() -- private key blobs +// XCP_CPB_UNWRAP_SYMM +// - UnwrapKey() -- symmetric blobs +// XCP_CPB_KEYGEN_ASYMM +// - GenerateKeyPair() +// XCP_CPB_KEYGEN_SYMM +// - GenerateKey() +// - UnwrapKey() -- symmetric target +// - DeriveKey() -- all targets, except openblockchain t-cert +// -- derivation, are symmetric +// XCP_CPB_RETAINKEYS +// - WrapKey(), the form which turns blob into SRK (handle+object) +// XCP_CPB_SKIP_KEYTESTS +// - GenerateKeyPair() +// - UnwrapKey() +// -- note: this functionality can only be verified based on logs +// -- it enables cross-checking opaque to the host +// XCP_CPB_NON_ATTRBOUND +// - WrapKey() -- when wrapping to non-AB form +// - UnwrapKey() -- when accepting non-AB form +// XCP_CPB_MODIFY_OBJECTS +// - SetAttributeValue() -- globally, not just per object +// XCP_CPB_RNG_SEED +// - SeedRandom() +// XCP_CPB_ALG_RAW_RSA +// - SignSingle() -- RSA blobs +// - Sign() -- RSA blobs +// - DecryptSingle() -- RSA blobs +// - Decrypt() -- RSA blobs +// XCP_CPB_ALG_NFIPS2009 +// - see NIST algorithms +// XCP_CPB_ALG_NBSI2009 +// - see BSI algorithms +// XCP_CPB_KEYSZ_HMAC_ANY +// - SignSingle() -- symmetric blobs with HMAC mech +// - Sign() -- symmetric blobs with HMAC mech +// - VerifySingle() -- symmetric blobs with HMAC mech +// - Verify() -- symmetric blobs with HMAC mech +// XCP_CPB_KEYSZ_BELOW80BIT +// - see size restrictions +// XCP_CPB_KEYSZ_80BIT +// - see size restrictions +// XCP_CPB_KEYSZ_112BIT +// - see size restrictions +// XCP_CPB_KEYSZ_128BIT +// - see size restrictions +// XCP_CPB_KEYSZ_192BIT +// - see size restrictions +// XCP_CPB_KEYSZ_256BIT +// - see size restrictions +// XCP_CPB_KEYSZ_RSA65536 +// - GenerateKeyPair() +// - UnwrapKey() +// XCP_CPB_ALG_RSA +// - GenerateKeyPair() -- CKK_RSA +// - UnwrapKey() -- CKK_RSA +// - SignSingle() -- RSA blobs +// - Sign() -- RSA blobs +// - VerifySingle() -- RSA blobs +// - Verify() -- RSA blobs +// XCP_CPB_ALG_DSA +// - GenerateKeyPair() -- CKK_DSA +// - UnwrapKey() -- CKK_DSA +// - SignSingle() -- DSA blobs +// - Sign() -- DSA blobs +// XCP_CPB_ALG_EC +// - GenerateKeyPair() -- CKK_EC +// - UnwrapKey() -- CKK_EC +// - SignSingle() -- EC blobs +// - Sign() -- EC blobs +// XCP_CPB_ALG_EC_BPOOLCRV +// - GenerateKeyPair() -- CKK_EC with Brainpool curves +// - UnwrapKey() -- CKK_EC with Brainpool curves +// XCP_CPB_ALG_EC_NISTCRV +// - GenerateKeyPair() -- CKK_EC with NIST curves +// - UnwrapKey() -- CKK_EC with NIST curves +// XCP_CPB_ALG_NFIPS2011 +// - see NIST algorithms +// XCP_CPB_ALG_NBSI2011 +// - see BSI algorithms +// XCP_CPB_USER_SET_TRUSTED +// - SetAttributeValue() +// XCP_CPB_ALG_SKIP_CROSSCHK +// XCP_CPB_WRAP_CRYPT_KEYS +// - unwrap_blob() -- all blob uses +// XCP_CPB_SIGN_CRYPT_KEYS +// - unwrap_blob() -- all blob uses +// XCP_CPB_WRAP_SIGN_KEYS +// - unwrap_blob() -- all blob uses +// XCP_CPB_USER_SET_ATTRBOUND +// - SetAttributeValue() +// XCP_CPB_ALLOW_PASSPHRASE +// - DeriveKey() +// XCP_CPB_WRAP_STRONGER_KEY +// - WrapKey() +// - UnwrapKey() +// XCP_CPB_WRAP_WITH_RAW_SPKI +// - WrapKey() +// /*-- /CP checks --------------------*/ + + /*--- administration -----------------------------------------------------*/ + #define XCP_ADM_QUERY 0x10000 + typedef enum { XCP_ADM_ADMIN_LOGIN = 1, // add admin certificate XCP_ADM_DOM_ADMIN_LOGIN = 2, // add domain admin certificate @@ -949,24 +1498,32 @@ XCP_ADM_DOM_ADMIN_LOGOUT = 4, // revoke domain admin certificate XCP_ADM_ADMIN_REPLACE = 5, // transition admin certificate XCP_ADM_DOM_ADMIN_REPLACE = 6, // transition domain admin certificate + XCP_ADM_SET_ATTR = 7, // set card attribute/s XCP_ADM_DOM_SET_ATTR = 8, // set domain attribute/ + XCP_ADM_GEN_DOM_IMPORTER = 9, // generate new importer (PK) key XCP_ADM_GEN_WK = 10, // create random domain WK XCP_ADM_EXPORT_WK = 11, // wrap+output WK or parts + XCP_ADM_EXPORT_NEXT_WK = 38, // wrap+output next WK or parts XCP_ADM_IMPORT_WK = 12, // set (set of) WK (parts) to pending XCP_ADM_COMMIT_WK = 13, // activate pending WK XCP_ADM_FINALIZE_WK = 14, // remove previous WK's + XCP_ADM_ZEROIZE = 15, // release CSPs from entire module XCP_ADM_DOM_ZEROIZE = 16, // release CSPs from domain/s + XCP_ADM_DOM_CTRLPOINT_SET = 17, // fix domain control points XCP_ADM_DOM_CTRLPOINT_ADD = 18, // enable domain control points XCP_ADM_DOM_CTRLPOINT_DEL = 19, // disable domain control points + XCP_ADM_SET_CLOCK = 20, // set module-internal UTC time XCP_ADM_SET_FCV = 21, // set function-control vector + XCP_ADM_CTRLPOINT_SET = 22, // fix card control points XCP_ADM_CTRLPOINT_ADD = 23, // enable card control points XCP_ADM_CTRLPOINT_DEL = 24, // disable card control points + XCP_ADM_REENCRYPT = 25, // transform blobs to next WK XCP_ADM_RK_REMOVE = 26, // remove (semi-) retained key XCP_ADM_CLEAR_WK = 27, // erase current WK @@ -981,6 +1538,9 @@ XCP_ADM_SET_TRUSTED = 35, // activate TRUSTED attribute on // blob/SPKI XCP_ADM_DOMAINS_ZEROIZE = 36, // multi-domain zeroize +// XCP_ADM_EXPORT_NEXT_WK = 38, // placeholder, find real entry above + XCP_ADM_SESSION_REMOVE = 39, // remove all or selected sessions + XCP_ADMQ_ADMIN = 1 | XCP_ADM_QUERY, // admin SKI/cert XCP_ADMQ_DOMADMIN = 2 | XCP_ADM_QUERY, // domain adm. SKI/cert XCP_ADMQ_DEVICE_CERT = 3 | XCP_ADM_QUERY, // module CA (OA) cert @@ -1004,22 +1564,30 @@ // current migration importer XCP_ADMQ_AUDIT_STATE = 16 | XCP_ADM_QUERY, // audit state entry or event count - XCP_ADMQ_LASTCMD_DOM_MASK = 17 | XCP_ADM_QUERY + XCP_ADMQ_LASTCMD_DOM_MASK = 17 | XCP_ADM_QUERY, // domain-bitmask affected by last // state-related administrative // command (export, import) + XCP_ADMQ_SVCADMIN = 18 | XCP_ADM_QUERY, // svc admin SKI/cert } XCP_Admcmd_t; + typedef enum { XCP_ADMINT_SIGN_THR = 1, // signature threshold XCP_ADMINT_REVOKE_THR = 2, // revocation (signature) threshold XCP_ADMINT_PERMS = 3, // permissions XCP_ADMINT_MODE = 4, // operating mode XCP_ADMINT_STD = 5, // standards' compliance - XCP_ADMINT_IDX_MAX = XCP_ADMINT_STD + XCP_ADMINT_PERMS_EXT01 = 6, // permissions (extension #1) + XCP_ADMINT_IDX_MAX = XCP_ADMINT_PERMS_EXT01 } XCP_AdmAttr_t; + #define XCP_ADMIN_ATTRIBUTE_COUNT XCP_ADMINT_IDX_MAX + +// init-time value #define XCP_ADM_SIGTHR__DEFAULT 0 #define XCP_ADM_REVTHR__DEFAULT 0 + +// permissions #define XCP_ADMP_WK_IMPORT 1 // allow WK import #define XCP_ADMP_WK_EXPORT 2 // allow WK export #define XCP_ADMP_WK_1PART 4 // allow WK transport in one part @@ -1028,6 +1596,7 @@ // (threshold set to 1) #define XCP_ADMP_CP_1SIGN 0x20 // allow single-signed CP modification #define XCP_ADMP_ZERO_1SIGN 0x40 // allow single-signed zeroize +// #define XCP_ADMP_NO_DOMAIN_IMPRINT \ 0x0080 // prohibit logging in to domains in // imprint mode (card only) @@ -1037,6 +1606,14 @@ // (ignored by domains) #define XCP_ADMP_STATE_1PART 0x0400 // allow state transport with 1-part // key (ignored by domains) +#define XCP_ADMP_DO_NOT_DISTURB 0x2000 // do not count module-administrator + // signatures for domain commands, + // other than zeroize commands + // (managed but ignored for module- + // level attributes) +// +// if adding other change-control bits, also update: +// #define XCP_ADMP_CHG_WK_IMPORT 0x10000 // allow changing WK import flag #define XCP_ADMP_CHG_WK_EXPORT 0x20000 // allow changing WK export flag #define XCP_ADMP_CHG_WK_1PART 0x40000 // allow changing WK 1-part @@ -1057,6 +1634,38 @@ // (ignored by domains) #define XCP_ADMP_CHG_ST_1PART 0x08000000 // allow changing 1-part encrypt bit // (ignored by domains) +#define XCP_ADMP_CHG_DO_NOT_DISTURB \ + 0x80000000 // allow changing the corresponding + // Do Not Disturb bit + +// +// permissions (extension 01) +// +#define XCP_ADMP_NQS_OA_SIGNATURES 1 // enable non-quantum-safe OA signat. +#define XCP_ADMP_QS_OA_SIGNATURES 2 // enable quantum-safe OA signatures +#define XCP_ADMP_NQS_ADM_SIGNATURES 4 // enable non-quantum-safe adm signat. +#define XCP_ADMP_QS_ADM_SIGNATURES 8 // enable quantum-safe adm signatures + +#define XCP_ADMP_CHG_NQS_OA_SIGNATURES \ + 0x10000 // allow changing the corresponding + // non-quantum-safe OA signature bit +#define XCP_ADMP_CHG_QS_OA_SIGNATURES \ + 0x20000 // allow changing the corresponding + // quantum-safe OA signature bit +#define XCP_ADMP_CHG_NQS_ADM_SIGNATURES \ + 0x40000 // allow changing the corresponding + // non-quantum-safe adm signature bit +#define XCP_ADMP_CHG_QS_ADM_SIGNATURES \ + 0x80000 // allow changing the corresponding + // quantum-safe adm signature bit + + +// +// if adding other change-control bits, also update: +// prevented_perm_changes() +// valid_attr_reactivate() +// ...as well as constants below +// #define XCP_ADMP__CHGBITS \ (XCP_ADMP_CHG_WK_IMPORT | \ XCP_ADMP_CHG_WK_EXPORT | \ @@ -1069,63 +1678,244 @@ XCP_ADMP_CHG_ZERO_1SIGN | \ XCP_ADMP_CHG_ST_IMPORT | \ XCP_ADMP_CHG_ST_EXPORT | \ - XCP_ADMP_CHG_ST_1PART) -#define XCP_ADMP__DEFAULT \ - (XCP_ADMP_WK_IMPORT | \ - XCP_ADMP_1SIGN | \ + XCP_ADMP_CHG_ST_1PART | \ + XCP_ADMP_CHG_DO_NOT_DISTURB) +// +#define XCP_ADMP__PERMS \ + (XCP_ADMP_WK_IMPORT | \ + XCP_ADMP_WK_EXPORT | \ + XCP_ADMP_WK_1PART | \ + XCP_ADMP_WK_RANDOM | \ + XCP_ADMP_1SIGN | \ + XCP_ADMP_CP_1SIGN | \ + XCP_ADMP_ZERO_1SIGN | \ + XCP_ADMP_NO_DOMAIN_IMPRINT | \ + XCP_ADMP_STATE_IMPORT | \ + XCP_ADMP_STATE_EXPORT | \ + XCP_ADMP_STATE_1PART | \ + XCP_ADMP_DO_NOT_DISTURB) +// +// CHGBITS / PERMS (extension 01) +#define XCP_ADMP__CHGBITS_EXT01 \ + (XCP_ADMP_CHG_NQS_OA_SIGNATURES | \ + XCP_ADMP_CHG_QS_OA_SIGNATURES | \ + XCP_ADMP_CHG_NQS_ADM_SIGNATURES | \ + XCP_ADMP_CHG_QS_ADM_SIGNATURES) +// +#define XCP_ADMP__PERMS_EXT01 \ + (XCP_ADMP_NQS_OA_SIGNATURES | \ + XCP_ADMP_QS_OA_SIGNATURES | \ + XCP_ADMP_NQS_ADM_SIGNATURES | \ + XCP_ADMP_QS_ADM_SIGNATURES) +// +#define XCP__ADMP_SUP_EXT01 (XCP_ADMP__PERMS_EXT01 | \ + XCP_ADMP__CHGBITS_EXT01) +// +// +#define XCP_ADMP__DEFAULT \ + (XCP_ADMP_WK_IMPORT | \ + XCP_ADMP_1SIGN | \ XCP_ADMP__CHGBITS) -#define XCP_ADMP__CARD_MASK \ - ~(XCP_ADMP_WK_IMPORT | \ - XCP_ADMP_WK_EXPORT | \ - XCP_ADMP_WK_1PART | \ - XCP_ADMP_WK_RANDOM | \ - XCP_ADMP_CP_1SIGN | \ - XCP_ADMP_CHG_WK_IMPORT | \ - XCP_ADMP_CHG_WK_EXPORT | \ - XCP_ADMP_CHG_WK_1PART | \ - XCP_ADMP_CHG_WK_RANDOM | \ +// +#define XCP_ADMP__DEFAULT_EXT01 \ + (XCP_ADMP__CHGBITS_EXT01 | \ + XCP_ADMP_NQS_OA_SIGNATURES | \ + XCP_ADMP_QS_OA_SIGNATURES | \ + XCP_ADMP_NQS_ADM_SIGNATURES | \ + XCP_ADMP_QS_ADM_SIGNATURES) +// +#define XCPM_ADMP__MODULE_DEFAULTS_MASK \ + (XCP_ADMP_DO_NOT_DISTURB | \ + XCP_ADMP_CHG_DO_NOT_DISTURB) +// +#define XCPM_ADMP__MODULE_DEFAULTS_MASK_EXT01 \ + (XCP_ADMP_NQS_OA_SIGNATURES | \ + XCP_ADMP_CHG_NQS_OA_SIGNATURES | \ + XCP_ADMP_QS_OA_SIGNATURES | \ + XCP_ADMP_CHG_QS_OA_SIGNATURES | \ + XCP_ADMP_NQS_ADM_SIGNATURES | \ + XCP_ADMP_CHG_NQS_ADM_SIGNATURES | \ + XCP_ADMP_QS_ADM_SIGNATURES | \ + XCP_ADMP_CHG_QS_ADM_SIGNATURES) +// +#define XCP_ADMP__CARD_MASK \ + ~(XCP_ADMP_WK_IMPORT | \ + XCP_ADMP_WK_EXPORT | \ + XCP_ADMP_WK_1PART | \ + XCP_ADMP_WK_RANDOM | \ + XCP_ADMP_CP_1SIGN | \ + XCP_ADMP_CHG_WK_IMPORT | \ + XCP_ADMP_CHG_WK_EXPORT | \ + XCP_ADMP_CHG_WK_1PART | \ + XCP_ADMP_CHG_WK_RANDOM | \ XCP_ADMP_CHG_CP_1SIGN) -#define XCP_ADMP__DOM_MASK \ - ~(XCP_ADMP_NO_DOMAIN_IMPRINT | \ - XCP_ADMP_STATE_IMPORT | \ - XCP_ADMP_STATE_EXPORT | \ - XCP_ADMP_STATE_1PART | \ - XCP_ADMP_CHG_ST_IMPORT | \ - XCP_ADMP_CHG_ST_EXPORT | \ +// +#define XCP_ADMP__CARD_MASK_EXT01 \ + ~(0U) +// +#define XCP_ADMP__DOM_MASK \ + ~(XCP_ADMP_NO_DOMAIN_IMPRINT | \ + XCP_ADMP_STATE_IMPORT | \ + XCP_ADMP_STATE_EXPORT | \ + XCP_ADMP_STATE_1PART | \ + XCP_ADMP_CHG_ST_IMPORT | \ + XCP_ADMP_CHG_ST_EXPORT | \ XCP_ADMP_CHG_ST_1PART) -#define XCP_ADMM_AUTHENTICATED 1 // no longer in imprint mode -#define XCP_ADMM_EXTWNG 2 // zeroize if starting w/ ext. warning - // included in default setup -#define XCP_ADMM_STR_112BIT 4 // require 112+ bits' admin strength -#define XCP_ADMM_STR_128BIT 8 // require 128+ bits' admin strength -#define XCP_ADMM_STR_160BIT 0x10 // require 160+ bits' admin strength -#define XCP_ADMM_STR_192BIT 0x20 // require 192+ bits' admin strength -#define XCP_ADMM_STR_256BIT 0x40 // require 256 bits' admin strength -#define XCP_ADMM_WKCLEAN_EXTWNG 0x80 // zeroize WKs if starting with - // ext. warning set. Leaves - // other parameters unaffected -#define XCP_ADMM_BATT_LOW 0x0100 // module reports low battery - // (read only) -#define XCP_ADMM_API_ACTIVE 0x0200 // remove to disable XCP within card +// +#define XCP_ADMP__DOM_MASK_EXT01 \ + ~(0U) +// + +#define XCP__ADMP_SUP ((XCP_ADMP__PERMS | XCP_ADMP__CHGBITS) &\ + ~XCP_ADMP_NOT_SUP) + +// card modes +#define XCP_ADMM_AUTHENTICATED 1U // no longer in imprint mode +#define XCP_ADMM_EXTWNG 2U // zeroize if starting w/ ext. + // warning included in default setup +// +// minimum administrator strength +#define XCP_ADMM_STR_112BIT 4U // require 112+ bits' admin strength +#define XCP_ADMM_STR_128BIT 8U // require 128+ bits' admin strength +#define XCP_ADMM_STR_160BIT 0x10U // require 160+ bits' admin strength +#define XCP_ADMM_STR_192BIT 0x20U // require 192+ bits' admin strength +#define XCP_ADMM_STR_256BIT 0x40U // require 256 bits' admin strength +#define XCP_ADMM_WKCLEAN_EXTWNG 0x80U // zeroize WKs if starting with + // ext. warning set. Leaves + // other parameters unaffected +#define XCP_ADMM_BATT_LOW 0x0100U // module reports low battery + // (read only) +#define XCP_ADMM_API_ACTIVE 0x0200U // remove to disable XCP within card +// #define XCP_ADMM__DEFAULT \ (XCP_ADMM_EXTWNG | \ XCP_ADMM_API_ACTIVE) +// +// all defined attributes +#define XCP_ADMM__MASK \ + (XCP_ADMM_AUTHENTICATED | \ + XCP_ADMM_EXTWNG | \ + XCP_ADMM_STR_112BIT | \ + XCP_ADMM_STR_128BIT | \ + XCP_ADMM_STR_160BIT | \ + XCP_ADMM_STR_192BIT | \ + XCP_ADMM_STR_256BIT | \ + XCP_ADMM_WKCLEAN_EXTWNG | \ + XCP_ADMM_BATT_LOW | \ + XCP_ADMM_API_ACTIVE) +// +// infrastructure modes read only on domain level +#define XCP_ADMM__CARD_ONLY_ATTR \ + (XCP_ADMM_EXTWNG | \ + XCP_ADMM_WKCLEAN_EXTWNG | \ + XCP_ADMM_API_ACTIVE) +// +#define XCP_ADMM__READ_ONLY_ATTR \ + (XCP_ADMM_AUTHENTICATED | \ + XCP_ADMM_BATT_LOW) + +// strength bits restrict adm key strength +#define XCP__ADMM_ADMSTR \ + (XCP_ADMM_STR_112BIT | \ + XCP_ADMM_STR_128BIT | \ + XCP_ADMM_STR_160BIT | \ + XCP_ADMM_STR_192BIT | \ + XCP_ADMM_STR_256BIT) + +#define XCP__ADMM_SUP XCP_ADMM__MASK + +// specific standards' compliance suites #define XCP_ADMS_FIPS2009 1 // NIST, 80+ bits, -2011.01.01. #define XCP_ADMS_BSI2009 2 // BSI , 80+ bits, -2011.01.01. #define XCP_ADMS_FIPS2011 4 // NIST, 112+ bits, 2011.01.01.- #define XCP_ADMS_BSI2011 8 // BSI, 112+ bits, 2011.01.01.- +// +// two bits reserved but not yet reported #define XCP_ADMS_SIGG_IMPORT 0x10 // .de SigG, key import #define XCP_ADMS_SIGG 0x20 // .de SigG, no key import +// #define XCP_ADMS_BSICC2017 0x40 // BSI, EP11 Common Criteria EAL4 2017 +// +#define XCP_ADMS_FIPS2021 0x80 // NIST SP800-131A REV.2, 2021.01.01 +#define XCP_ADMS_FIPS2024 0x100 // NIST SP800-131A REV.2, 2024.01.01 +#define XCP_ADMS_ADM_FIPS2021 0x200 // NIST SP800-131A REV.2, 2021.01.01 + #define XCP_ADMS__ALL \ (XCP_ADMS_FIPS2009 | \ XCP_ADMS_BSI2009 | \ XCP_ADMS_FIPS2011 | \ XCP_ADMS_BSI2011 | \ + XCP_ADMS_BSICC2017 | \ + XCP_ADMS_FIPS2021 | \ + XCP_ADMS_FIPS2024 | \ + XCP_ADMS_ADM_FIPS2021) + +#define XCP_ADMS__SUPP (XCP_ADMS__ALL & \ + ~(XCP_ADMS_FIPS2021 | \ + XCP_ADMS_ADM_FIPS2021 | \ + XCP_ADMS_FIPS2024)) + +// The following 'legacy' defines are used as default 'supported bit masks' +// for older devices that do not have native bit masks for that purpose. +// Note: If supported bits are not present, the import of these bits are +// skipped and the default values will be kept. +#define XCP__ADMP_SUP_LEGACY \ + (XCP_ADMP_WK_IMPORT | \ + XCP_ADMP_WK_EXPORT | \ + XCP_ADMP_WK_1PART | \ + XCP_ADMP_WK_RANDOM | \ + XCP_ADMP_1SIGN | \ + XCP_ADMP_CP_1SIGN | \ + XCP_ADMP_ZERO_1SIGN | \ + XCP_ADMP_NO_DOMAIN_IMPRINT | \ + XCP_ADMP_STATE_IMPORT | \ + XCP_ADMP_STATE_EXPORT | \ + XCP_ADMP_STATE_1PART | \ + XCP_ADMP_CHG_WK_IMPORT | \ + XCP_ADMP_CHG_WK_EXPORT | \ + XCP_ADMP_CHG_WK_1PART | \ + XCP_ADMP_CHG_WK_RANDOM | \ + XCP_ADMP_CHG_SIGN_THR | \ + XCP_ADMP_CHG_REVOKE_THR | \ + XCP_ADMP_CHG_1SIGN | \ + XCP_ADMP_CHG_CP_1SIGN | \ + XCP_ADMP_CHG_ZERO_1SIGN | \ + XCP_ADMP_CHG_ST_IMPORT | \ + XCP_ADMP_CHG_ST_EXPORT | \ + XCP_ADMP_CHG_ST_1PART) + +#define XCP__ADMM_SUP_LEGACY \ + (XCP_ADMM_AUTHENTICATED | \ + XCP_ADMM_EXTWNG | \ + XCP_ADMM_WKCLEAN_EXTWNG | \ + XCP_ADMM_BATT_LOW | \ + XCP_ADMM_API_ACTIVE) + +#define XCP_ADMS__ALL_LEGACY \ + (XCP_ADMS_FIPS2009 | \ + XCP_ADMS_BSI2009 | \ + XCP_ADMS_FIPS2011 | \ + XCP_ADMS_BSI2011 | \ XCP_ADMS_BSICC2017) -#define XCP_ADMS_IS_BSI(mode) (!!(mode & (XCP_ADMS_BSI2009 | \ - XCP_ADMS_BSI2011 | \ - XCP_ADMS_BSICC2017 )) ) + +#define XCP__ADMP_SUP_EXT01_LEGACY (0) + +// has compliance any BSI mode +#define XCP_ADMS_IS_BSI(mode) (!!((mode) & (XCP_ADMS_BSI2009 | \ + XCP_ADMS_BSI2011 | \ + XCP_ADMS_BSICC2017 )) ) +// mask of supported import keys +// 3k and 4k RSA are not supported +#define XCP_ADM_IMPEXP_KEYS__MASK \ + ((1 << XCP_IMPRKEY_RSA_2048) | \ + (1 << XCP_IMPRKEY_EC_P256) | \ + (1 << XCP_IMPRKEY_EC_P521) | \ + (1 << XCP_IMPRKEY_EC_BP256r) | \ + (1 << XCP_IMPRKEY_EC_BP320r) | \ + (1 << XCP_IMPRKEY_EC_BP512r) | \ + (1 << XCP_IMPRKEY_EC_P521_TKE)) + + /*--- audit chains -------------------------------------------------------*/ #define XCP_LOG_KEYREC_BYTES 24 #define XCP_LOG_SEQNR_BYTES 6 @@ -1141,12 +1931,14 @@ #define XCP_LOG_SALT_MAX_BYTES \ (XCP_LOG_SALT_MAX_UNITS * XCP_LOG_SALTUNIT_BYTES) #define XCP_LOG_PRFSALT_BYTES ((size_t) 64/8) /* Siphash-2-4 */ + /* event context: fields present in all audit records */ #define XCP_LOG_CONTEXT_BYTES \ (2* XCP_SERIALNR_CHARS+ \ 2+2+ /* audit instance, event type */ \ 4+4+ /* event type, firmware ID */ \ 4+4 /* fn ID, domain, var-len size */ ) + /* optional fields, total (see flags) */ #define XCP_LOG_OPTFIELD_MAX_BYTES \ (2* XCP_WK_BYTES + \ @@ -1156,10 +1948,12 @@ XCP_LOG_COMPLIANCE_BYTES + \ XCP_LOG_REASON_BYTES + \ XCP_LOG_SALT_MAX_BYTES) + #define XCP_LOG_HEADER_BYTES \ (1+1+2 + /* type, version, bytecount */ \ XCP_LOG_SEQNR_BYTES + \ XCP_LOG_TIMET_BYTES) + /* worst-case full wire-formatted entry, incl. trailing hash */ #define XCP_LOG_ENTRY_MAX_BYTES \ (XCP_LOG_HEADER_BYTES + \ @@ -1167,55 +1961,65 @@ XCP_LOG_CONTEXT_BYTES + \ XCP_LOG_OPTFIELD_MAX_BYTES + \ XCP_LOG_STATE_BYTES) + + /*--- state serialization ------------------------------------------------*/ typedef enum { - XCP_STSTYPE_SECTIONCOUNT = 1, // section count +file hash - XCP_STSTYPE_DOMAINIDX_MAX = 2, // largest index +total nr of domains - XCP_STSTYPE_DOMAINS_MASK = 3, // bitmask of included domains - XCP_STSTYPE_SERIALNR = 4, - XCP_STSTYPE_CREATE_TIME = 5, // file date/time (UTC) - XCP_STSTYPE_FCV = 6, // public parts of originating FCV - XCP_STSTYPE_CARD_QUERY = 7, // card state structure (xcp_info) - XCP_STSTYPE_CARD_ADM_SKIS = 8, // card admin SKIs, packed - XCP_STSTYPE_CARD_ADM_CERTS = 9, // card admin certificates, packed - XCP_STSTYPE_DOM_ADM_SKIS = 10, // domain admin SKIs, packed - XCP_STSTYPE_DOM_ADM_CERTS = 11, // domain admin certificates, packed - XCP_STSTYPE_DOM_QUERY = 12, // domain state structure (xcp_info) - XCP_STSTYPE_KPH_SKIS = 13, // count and SKIs of targeted KPHs - XCP_STSTYPE_CARD_ATTRS = 14, // card attributes - XCP_STSTYPE_DOM_ATTRS = 15, // domain attributes - XCP_STSTYPE_CARD_TRANSCTR = 16, // card transaction counter - XCP_STSTYPE_DOM_TRANSCTR = 17, // domain transaction counter - XCP_STSTYPE_WK_ENCR_ALG = 18, - XCP_STSTYPE_WK_ENCR_DATA = 19, - XCP_STSTYPE_SIG_CERT_COUNT = 20, - XCP_STSTYPE_SIG_CERTS = 21, - XCP_STSTYPE_FILE_SIG = 22, - XCP_STSTYPE_DOM_CPS = 23, // full set of control points - XCP_STSTYPE_STATE_SALT = 24, - XCP_STSTYPE_KEYPART = 25, // encrypted keypart (RecipientInfo) - XCP_STSTYPE_KEYPART_SIG = 26, // signature on encrypted keypart - XCP_STSTYPE_KEYPART_COUNT = 27, // total number of keyparts - XCP_STSTYPE_KEYPART_LIMIT = 28, // number of keyparts needed to - // restore - XCP_STSTYPE_KEYPART_CERT = 29, // certificate of keypart holder - XCP_STSTYPE_CERT_AUTH = 30, // certificate authority issuing - // some of the certificates. This - // field contains host-supplied data - // and it is ignored by EP11 itself. - XCP_STSTYPE_STATE_SCOPE = 31, // restriction on contents of full - // state structure - XCP_STSTYPE_MULTIIMPORT_MASK - = 32, // import only: designate import - // request to be replicated into - // multiple recipient domains - XCP_STSTYPE_CPS_MASK = 33, // bitmask of all CPs supported - // by the exporting module - XCP_STSTYPE_MAX = XCP_STSTYPE_CPS_MASK + XCP_STSTYPE_SECTIONCOUNT = 1, // section count +file hash + XCP_STSTYPE_DOMAINIDX_MAX = 2, // largest index +total nr of doms + XCP_STSTYPE_DOMAINS_MASK = 3, // bitmask of included domains + XCP_STSTYPE_SERIALNR = 4, + XCP_STSTYPE_CREATE_TIME = 5, // file date/time (UTC) + XCP_STSTYPE_FCV = 6, // public parts of originating FCV + XCP_STSTYPE_CARD_QUERY = 7, // V0 card state struct (xcp_info) + XCP_STSTYPE_CARD_ADM_SKIS = 8, // card admin SKIs, packed + XCP_STSTYPE_CARD_ADM_CERTS = 9, // card admin certificates, packed + XCP_STSTYPE_DOM_ADM_SKIS = 10, // domain admin SKIs, packed + XCP_STSTYPE_DOM_ADM_CERTS = 11, // domain admin certs, packed + XCP_STSTYPE_DOM_QUERY = 12, // domain state struct (xcp_info) + XCP_STSTYPE_KPH_SKIS = 13, // count and SKIs of targeted KPHs + XCP_STSTYPE_CARD_ATTRS = 14, // card attributes + XCP_STSTYPE_DOM_ATTRS = 15, // domain attributes + XCP_STSTYPE_CARD_TRANSCTR = 16, // card transaction counter + XCP_STSTYPE_DOM_TRANSCTR = 17, // domain transaction counter + XCP_STSTYPE_WK_ENCR_ALG = 18, + XCP_STSTYPE_WK_ENCR_DATA = 19, + XCP_STSTYPE_SIG_CERT_COUNT = 20, + XCP_STSTYPE_SIG_CERTS = 21, + XCP_STSTYPE_FILE_SIG = 22, + XCP_STSTYPE_DOM_CPS = 23, // full set of control points + XCP_STSTYPE_STATE_SALT = 24, + XCP_STSTYPE_KEYPART = 25, // encrypted keypart (RecipientInfo) + XCP_STSTYPE_KEYPART_SIG = 26, // signature on encrypted keypart + XCP_STSTYPE_KEYPART_COUNT = 27, // total number of keyparts + XCP_STSTYPE_KEYPART_LIMIT = 28, // number of keyparts needed to + // restore + XCP_STSTYPE_KEYPART_CERT = 29, // certificate of keypart holder + XCP_STSTYPE_CERT_AUTH = 30, // certificate authority issuing + // some of the certificates. This + // field contains host-supplied data + // and it is ignored by EP11 itself. + XCP_STSTYPE_STATE_SCOPE = 31, // restriction on contents of full + // state structure + XCP_STSTYPE_MULTIIMPORT_MASK = 32, // import only: designate import + // request to be replicated into + // multiple recipient domains + XCP_STSTYPE_CPS_MASK = 33, // bitmask of all CPs supported + // by the exporting module + XCP_STSTYPE_CARD_QUERY_V1 = 34, // V1 card state struct (xcp_info) + XCP_STSTYPE_CARD_QUERY_V2 = 35, // V2 card state struct (xcp_info) + XCP_STSTYPE_CARD_EXTADM_SKIS = 36, // ext. card admin SKIs, packed + XCP_STSTYPE_CARD_EXTADM_CERTS = 37, // ext. card admin certs, packed + XCP_STSTYPE_DOM_EXTADM_SKIS = 38, // ext. dom admin SKIs, packed + XCP_STSTYPE_DOM_EXTADM_CERTS = 39, // ext. dom admin certs, packed + + XCP_STSTYPE_MAX = XCP_STSTYPE_DOM_EXTADM_CERTS } XCP_StateSection_t; + typedef enum { XCP_STALG_AES256_CBC = 1 } XCP_StateEncrAlg_t; + typedef enum { XCP_FILEID_SAVED_STATE = 1, // serialized state XCP_FILEID_KEYPARTS = 2, // encrypted keyparts @@ -1223,6 +2027,8 @@ XCP_FILEID_EXPREQUEST = 4, // export request XCP_FILEID_MAX = XCP_FILEID_EXPREQUEST } XCP_FileId_t; + + typedef enum { XCP_STDATA_DOMAIN = 1, // state restricted to domain data // only, excluding card-specific @@ -1231,11 +2037,23 @@ // non-sensitive sections only XCP_STWK_KP_NO_CERT = 4, // keypart section restricted to // not return KPH certificates - XCP_STDATA_MAX = ((XCP_STWK_KP_NO_CERT *2) -1) + XCP_STWK_KP_NO_OA_CHAIN = 8, // keypart section restricted to + // not return OA certificate chain + XCP_STDATA_NQS = 0x20,// allow use of non-quantum-safe + // algorithms in KP export/signature + XCP_STDATA_QS = 0x40,// allow use of quantum-safe + // algorithms in KP export/signature + XCP_STDATA_MAX = ((XCP_STDATA_QS *2) -1) } XCP_StateType_t; + +// type || identifier prefixes #define XCP_STSTYPE_TYPE_BYTES 2 #define XCP_STSTYPE_TYPEID_BYTES 4 + + /*--- EC curves ----------------------------------------------------------*/ + +// NIST/SECG object identifiers #define XCP_EC_P192 "\x06\x08\x2a\x86\x48\xce\x3d\x03\x01\x01" #define XCP_EC_P192_BYTES 10 #define XCP_EC_P224 "\x06\x05\x2b\x81\x04\x00\x21" @@ -1246,6 +2064,8 @@ #define XCP_EC_P384_BYTES 7 #define XCP_EC_P521 "\x06\x05\x2b\x81\x04\x00\x23" #define XCP_EC_P521_BYTES 7 + +// NIST/SECG, curve names as UTF-8/ASCII strings #define XCP_EC_P192_NAME "\x50\x2d\x31\x39\x32" /* P-192 */ #define XCP_EC_P192_NAME_BYTES 5 #define XCP_EC_P224_NAME "\x50\x2d\x32\x32\x34" /* P-224 */ @@ -1256,6 +2076,8 @@ #define XCP_EC_P384_NAME_BYTES 5 #define XCP_EC_P521_NAME "\x50\x2d\x35\x32\x31" /* P-521 */ #define XCP_EC_P521_NAME_BYTES 5 + +// Brainpool object identifiers #define XCP_EC_BP160R "\x06\x09\x2b\x24\x03\x03\x02\x08\x01\x01\x01" #define XCP_EC_BP160R_BYTES 11 #define XCP_EC_BP160T "\x06\x09\x2b\x24\x03\x03\x02\x08\x01\x01\x02" @@ -1285,7 +2107,10 @@ #define XCP_EC_BP512T "\x06\x09\x2b\x24\x03\x03\x02\x08\x01\x01\x0e" #define XCP_EC_BP512T_BYTES 11 #define XCP_EC_BPOID_BYTES 11 +// #define XCP_EC_BPOIDS 14 + +// Brainpool, curve names as UTF-8/ASCII strings #define XCP_EC_BP160R_NAME "\x42\x50\x2d\x31\x36\x30\x52" /* BP-160R */ #define XCP_EC_BP160R_NAME_BYTES 7 #define XCP_EC_BP160T_NAME "\x42\x50\x2d\x31\x36\x30\x54" /* BP-160T */ @@ -1314,31 +2139,43 @@ #define XCP_EC_BP512R_NAME_BYTES 7 #define XCP_EC_BP512T_NAME "\x42\x50\x2d\x35\x31\x32\x54" /* BP-512T */ #define XCP_EC_BP512T_NAME_BYTES 7 + +// secp256k1 (Bitcoin default curve) #define XCP_EC_S256K1 "\x06\x05" "\x2b\x81\x04\x00\x0a" #define XCP_EC_S256K1_BYTES 7 #define XCP_EC_S256K1_NAME "\x53\x45\x43\x50\x32\x35\x36\x4b\x31" /* SECP256K1 */ #define XCP_EC_S256K1_NAME_BYTES 9 + +// curve25519, curve448, related OIDs +// +// 1.3.101.110: curve25519, allocated by PKIX, ECDH only #define XCP_EC_X25519 "\x06\x03\x2b\x65\x6e" #define XCP_EC_X25519_BYTES 5 #define XCP_EC_X25519_NAME "\x63\x75\x72\x76\x65\x32\x35\x35\x31\x39" /* curve25519 */ #define XCP_EC_X25519_NAME_BYTES 10 +// +// 1.3.101.111: curve[of-ed]448 'Goldilocks', allocated by PKIX, ECDH only #define XCP_EC_X448 "\x06\x03\x2b\x65\x6f" #define XCP_EC_X448_BYTES 5 #define XCP_EC_X448_NAME "\x78\x34\x34\x38" /* c448, matching RFC8410 */ #define XCP_EC_X448_NAME_BYTES 4 +// +// 1.3.101.112: EDDSA, 25519 #define XCP_EC_DSA25519 "\x06\x03\x2b\x65\x70" #define XCP_EC_DSA25519_BYTES 5 #define XCP_EC_DSA25519_NAME "\x65\x64\x32\x35\x35\x31\x39" /* ed25519 */ #define XCP_EC_DSA25519_NAME_BYTES 7 +// 1.3.101.113: EDDSA/448 (ed448) #define XCP_EC_DSA448 "\x06\x03\x2b\x65\x71" #define XCP_EC_DSA448_BYTES 5 #define XCP_EC_DSA448_NAME "\x65\x64\x34\x34\x38" /* ed448 */ #define XCP_EC_DSA448_NAME_BYTES 5 + #define XCP_EC_MAX_ID_BYTES 11 /* fits all EC names/OIDs */ -#define XCP_PQC_DILITHIUM_65_NAME "\x6\xB\x2B\x6\x1\x4\x1\x2\x82\xB\x1\x6\x5" -#define XCP_PQC_DILITHIUM_65_NAME_BYTES 13 + + /*------------------------------------*/ typedef enum { XCP_EC_C_NIST_P192 = 1, /* NIST, FP curves */ @@ -1346,6 +2183,7 @@ XCP_EC_C_NIST_P256 = 3, XCP_EC_C_NIST_P384 = 4, XCP_EC_C_NIST_P521 = 5, + XCP_EC_C_BP160R = 6, /* Brainpool, FP curves */ XCP_EC_C_BP160T = 7, XCP_EC_C_BP192R = 8, @@ -1360,13 +2198,19 @@ XCP_EC_C_BP384T = 17, XCP_EC_C_BP512R = 18, XCP_EC_C_BP512T = 19, + XCP_EC_C_25519 = 20, /* curve25519, FP (2^255-19) */ XCP_EC_C_SECP256K1 = 23, /* secp256k1, Bitcoin default curve */ XCP_EC_C_ED448 = 24, /* ed448 ('Goldilocks') FP(2^448-2^244+1)*/ XCP_EC_C_448 = 25, /* c448/x448, ECDH only */ XCP_EC_C_ED25519 = 26, /* ed25519, EDDSA */ - XCP_EC_C_MAX = XCP_EC_C_ED25519 + + + XCP_EC_C_MAX = 27 /* last possible value */ + } XCP_ECcurve_t; + + /*-------------------------------------- * groups of EC curves, without specific OIDs */ @@ -1378,9 +2222,67 @@ XCP_EC_CG_C448 = 6, /* c448, ed448 ('Goldilocks') */ XCP_EC_CG_MAX = XCP_EC_CG_C448 } XCP_ECCurveGrp_t; + + +/*--- PQC algorithms ------------------------------------------------------*/ + +// Dilithium related OIDs +// Round 2 Dilithium-3 (5-4) +#define XCP_PQC_DILITHIUM_R2_54 "\x6\xb\x2b\x6\x1\x4\x1\x2\x82\xb\x1\x5\x4" +#define XCP_PQC_DILITHIUM_R2_54_BYTES 13 +// Round 2 Dilithium-4 (6-5) +#define XCP_PQC_DILITHIUM_R2_65 "\x6\xb\x2b\x6\x1\x4\x1\x2\x82\xb\x1\x6\x5" +#define XCP_PQC_DILITHIUM_R2_65_BYTES 13 +// Round 2 Dilithium-5 (8-7) +#define XCP_PQC_DILITHIUM_R2_87 "\x6\xb\x2b\x6\x1\x4\x1\x2\x82\xb\x1\x8\x7" +#define XCP_PQC_DILITHIUM_R2_87_BYTES 13 +// Round 3 Dilithium-2 (4-4) +#define XCP_PQC_DILITHIUM_R3_44 "\x6\xb\x2b\x6\x1\x4\x1\x2\x82\xb\x7\x4\x4" +#define XCP_PQC_DILITHIUM_R3_44_BYTES 13 +// Round 3 Dilithium-3 (6-5) +#define XCP_PQC_DILITHIUM_R3_65 "\x6\xb\x2b\x6\x1\x4\x1\x2\x82\xb\x7\x6\x5" +#define XCP_PQC_DILITHIUM_R3_65_BYTES 13 +// Round 3 Dilithium-5 (8-7) +#define XCP_PQC_DILITHIUM_R3_87 "\x6\xb\x2b\x6\x1\x4\x1\x2\x82\xb\x7\x8\x7" +#define XCP_PQC_DILITHIUM_R3_87_BYTES 13 + +// Round 2 Kyber 512 +#define XCP_PQC_KYBER_R2_512 "\x6\x9\x2B\x6\x1\x4\x1\x2\x82\xB\x5" +#define XCP_PQC_KYBER_R2_512_BYTES 11 + +// Round 2 Kyber 768 +#define XCP_PQC_KYBER_R2_768 "\x6\xB\x2B\x6\x1\x4\x1\x2\x82\xB\x5\x3\x3" +#define XCP_PQC_KYBER_R2_768_BYTES 13 + +// Round 2 Kyber 1024 +#define XCP_PQC_KYBER_R2_1024 "\x6\xB\x2B\x6\x1\x4\x1\x2\x82\xB\x5\x4\x4" +#define XCP_PQC_KYBER_R2_1024_BYTES 13 + +/*------------------------------------*/ +typedef enum { + XCP_PQC_S_DILITHIUM_R2_54 = 1, /* Round-2 Dilithium */ + XCP_PQC_S_DILITHIUM_R2_65 = 2, + XCP_PQC_S_DILITHIUM_R2_87 = 3, + XCP_PQC_S_DILITHIUM_R3_44 = 4, /* Round-3 Dilithium */ + XCP_PQC_S_DILITHIUM_R3_65 = 5, + XCP_PQC_S_DILITHIUM_R3_87 = 6, + XCP_PQC_S_KYBER_R2_512 = 7, /* Round-2 Kyber */ + XCP_PQC_S_KYBER_R2_768 = 8, + XCP_PQC_S_KYBER_R2_1024 = 9, + + XCP_PQC_MAX = XCP_PQC_S_KYBER_R2_1024, +} XCP_PQCStrength_t; + + +// binary encoding of function/version query +// SEQUENCE { OCTET STRING (0) } +// module responds with API version and build ID +// #define XCP_VERS_QUERY_REQ 0x30,0x03,0x04,0x01,0x00 /* request body */ #define XCP_VERS_QUERY_REQ_BYTES 5 + /*--- development-only test functions ------------------------------------*/ + typedef enum { XCP_DEV_SET_WK = 1, // set and activate (imprint) WK XCP_DEV_SET_NEXT_WK = 2, // set+commit next WK (+imprint) @@ -1413,6 +2315,7 @@ // recommended before exporting RNG // state, to maximize number of // matching bits after state is restored + XCP_DEVQ_ENTROPY = 23, // retrieve raw TRNG output // conditioned entropy, no DRNG // processing a direct-call subset of @@ -1422,13 +2325,17 @@ // setup during processing, // slowing it down // see also: XCP_DEV_RAWENTROPY + XCP_DEVQ_PERFMODE = 24, // query performance/timestamp setup XCP_DEV_PERFMODE = 25, // change performance/timestamp setup + XCP_DEV_RSA_DECR_CYCLE = 26, // RSA, raw mod. exponentiation, looped XCP_DEV_RSACRT_DECR_CYCLE = 27, // RSA, private exponent, CRT, looped XCP_DEV_ECMUL_CYCLE = 28, // EC scalar multiplication, looped + XCP_DEV_PERFMARK = 29, // add performance-test marker // LS 4 bits included in entry + XCP_DEVQ_PERF_LOCK = 30, // raw performance: un/lock cycles, // single thread // test on otherwise quiesced backend @@ -1439,6 +2346,7 @@ // timestamp/syslog/etc. entries // to simplify offline scaling of // performance management + XCP_DEV_CACHE_MODE = 33, // set or query module-internal cache // state and statistics XCP_DEVQ_CACHE_STATS = 34, // log cache-statistics summary @@ -1446,25 +2354,32 @@ XCP_DEV_DELAY = 35, // NOP: delay the backend thread by // a host-influenced amount of time, // without performing other operations + XCP_DEV_COMPRESS = 36, // return 'summarized' version of any // supplied data XCP_DEV_XOR_FF = 37, // returns a copy of data, all bits // flipped (XORed with 0xff) XCP_DEV_PRF = 38, // returns PRF stream from caller- // provided seed and bytecount + XCP_DEV_TRANSPORTSTATE1 = 39, // transport-statistics dump // (system-dependent functionality) + XCP_DEVQ_CACHEINDEX = 40, // return module-internal blob index // of caller-provided key XCP_DEVQ_CSP_OBJCOUNT = 41, // CSP-object reference counter, // if available + XCP_DEV_CSPTYPE = 42, // preferred CSP-object (engine) type + XCP_DEV_FCV = 43, // query and/or set current FCV // without signature verification XCP_DEV_CLEAR_FCV = 44, // erase any existing FCV + XCP_DEVQ_ASSERTIONS = 45, // verify the consistency of module- // internal data structures, as a // stronger form of assertion-checking + XCP_DEV_TEST_LATESTART = 46, // perform any initial test which has // been skipped during backend startup. // not necessary unless running against @@ -1472,6 +2387,7 @@ // settings [which trim down backend // testing to a bare minimum]. Safe to // issue, a NOP otherwise. + XCP_DEV_ENVSEED = 47, // seed backend with device-unique, // environment-derived, low quality // entropy [augments/replaces real @@ -1479,36 +2395,79 @@ // unrelated backends diverge even // when VM-hosted or otherwise lacking // proper initial entropy] + XCP_DEVQ_RAWENTROPY = 48, // retrieve raw entropy pool, before // compression, if backend supports // this (see Clic docs for raw-pool // state details) // // see also: XCP_DEV_ENTROPY + XCP_DEV_EC_SIGVER_CYCLE = 49, // EC sign/verify in loop // operation derived from supplied blob // (EC private/SPKI) // see also: XCP_DEV_ECMUL_CYCLE + XCP_DEV_DRAIN_ENTROPY = 50, // TRNG: force at least one collect // entropy->compression call // [may be more, depends on DRNG state] + XCP_DEV_CONV_EC_BLOB = 51, // CLiC blob conversion: Convert a // software Blob to a 4767 hardware blob // At the moment only EC blobs are // supported + XCP_DEVQ_COUNTERS = 52, // retrieve coverage counters // these are intentionally not published + XCP_DEV_RSACRT_MSG_CYCLE = 53, // RSA, private exponent, CRT, looped // this variant increments message // and returns per-message statistics + XCP_DEV_AUDIT_CYCLE = 54, // audit-log, generate log entries // in a loop - XCP_DEV_PQC_DILITHIUM = 55, // post-quantum algs: generic call + + XCP_DEV_EDDSA = 55, // EC dig.signature forms + + XCP_DEV_ECDH = 56, // EC Diffie-Hellman/Montgomery forms + + XCP_DEV_PQC_DILITHIUM = 57, // post-quantum algs: generic call // for Dilithium (from PQ Crystals) - XCP_DEV_MAX_INDEX = XCP_DEV_PQC_DILITHIUM + + XCP_DEV_ABORT = 63, // raise abort signal + XCP_DEV_DRNG = 64, // gen non-randomly-seeded DRNG bytes + XCP_DEV_DRNG_RESEED = 65, // explicitly set DRNG seed + XCP_DEV_FAULT_INJECT = 66, // control fault point injection + XCP_DEVQ_FAULTLIST = 67, // list available fault points + XCP_DEV_FLIP_ERRORSTATE = 68, // explicitly flip the setting of the + // error state of the module + XCP_DEV_AESKW = 69, + XCP_DEV_UNIT_TEST = 72, // run unit tests on module + + + XCP_DEV_MAX_INDEX = XCP_DEV_UNIT_TEST } XCP_DEVcmd_t; -#define XCP_DEV_MAX_DATABYTES ((size_t) 4096) +// +// upper limit on additional data bytes, for SYS-TEST commands with aux. data +// (arbitrary limit, commands may restict further) +#define XCP_DEV_MAX_DATABYTES ((size_t) 64000) +// +// iteration-count limit applies to any iterative call +// driver[timeout] may interfere; dev-only feature is not otherwise restricted #define XCP_DEV_MAX_ITERATIONS ((unsigned int) 128*1024) + +#define XCP_DEV_C25519 (unsigned int)255 +#define XCP_DEV_C448 (unsigned int)448 +#define XCP_DEV_ED25519 ~((unsigned int)255) +#define XCP_DEV_ED448 ~((unsigned int)448) +#define XCP_DEV_ED25519_2 ~((unsigned int)256) +#define XCP_DEV_ED448_2 ~((unsigned int)456) + +#define XCP_DEV_AESKW_WRAP (unsigned int)1 +#define XCP_DEV_AESKW_UNWRAP (unsigned int)2 +#define XCP_DEV_AESKW_WRAP_PAD (unsigned int)3 +#define XCP_DEV_AESKW_UNWRAP_PAD (unsigned int)4 + typedef enum { XCP_DEVC_CACHE_ACTIVE = 1, // blob-cache is available XCP_DEVC_CACHE_INACTIVE = 2, // caching suspended: lookups fail, @@ -1516,33 +2475,246 @@ XCP_DEVC_CACHE_FLUSH = 4, // evict all currently cached objects // available even if cache is suspended } XCP_DEVcache_t; + typedef enum { XCP_DEV_RNG_TRNG = 0, // no DRNG involvement XCP_DEV_RNG_DRNG = 1, // DRNG, no reseeding XCP_DEV_RNG_MIXED = 2, // DRNG, with TRNG reseeding - XCP_DEV_RNG_TYPE_MAX = XCP_DEV_RNG_MIXED + XCP_DEV_RNG_SWDRNG = 4, // Software-DRNG + XCP_DEV_RNG_TYPE_MAX = XCP_DEV_RNG_SWDRNG } XCP_DEVrng_t; + typedef enum { XCP_DEVFS_QUERY = 0, // current state query only XCP_DEVFS_READONLY = 1, // prevent writes XCP_DEVFS_NOACCESS = 2 // prevent all filesystem access } XCP_DEVfs_t; + +// size of coverage counters #define XCP_DEV_CTR_SIZE 4 #define XCP_DEV_CTR_TYPE uint32_t + +typedef enum { + XCP_DEV_FAULT_EXPR = 1, // evaluate to non-null if triggered + XCP_DEV_FAULT_FUNC = 2, // call callback function + XCP_DEV_FAULT_MSLEEP = 4, // sleep for msleep ms + XCP_DEV_FAULT_RV = 8, // faultpoint returns rv + XCP_DEV_FAULT_DBIT = 16, // flip bit at compile-time const offset + XCP_DEV_FAULT_DNULL = 32, // faultpoint memsets data to zero + XCP_DEV_FAULT_RBIT = 64, // flip bit at random offset +} XCP_DEVfault_t; + +// no vendor extension definition for CKG available yet #if !defined(CKG_VENDOR_DEFINED) #define CKG_VENDOR_DEFINED 0x80000000UL #endif + #define CKG_IBM_MGF1_SHA3_224 (CKG_VENDOR_DEFINED +1) #define CKG_IBM_MGF1_SHA3_256 (CKG_VENDOR_DEFINED +2) #define CKG_IBM_MGF1_SHA3_384 (CKG_VENDOR_DEFINED +3) #define CKG_IBM_MGF1_SHA3_512 (CKG_VENDOR_DEFINED +4) + +#if !defined(CKD_VENDOR_DEFINED) +#define CKD_VENDOR_DEFINED 0x80000000UL +#endif + +#define CKD_IBM_HYBRID_NULL (CKD_VENDOR_DEFINED + 0x00000001UL) +#define CKD_IBM_HYBRID_SHA1_KDF (CKD_VENDOR_DEFINED + 0x00000002UL) +#define CKD_IBM_HYBRID_SHA224_KDF (CKD_VENDOR_DEFINED + 0x00000003UL) +#define CKD_IBM_HYBRID_SHA256_KDF (CKD_VENDOR_DEFINED + 0x00000004UL) +#define CKD_IBM_HYBRID_SHA384_KDF (CKD_VENDOR_DEFINED + 0x00000005UL) +#define CKD_IBM_HYBRID_SHA512_KDF (CKD_VENDOR_DEFINED + 0x00000006UL) + +#define XCP_MODEL_CEX4P 4 +#define XCP_MODEL_CEX5P 5 +#define XCP_MODEL_CEX6P 6 +#define XCP_MODEL_CEX7P 7 +#define XCP_MODEL_CEX8P 8 + +/*--------------------------------------------------------------------------*/ +// max value for target groups +#define XCP_MAX_GRPIDX 1024u + +// +// macros for setting/checking and removing domains from (tgt.mgmt) domain mask +#define XCPTGTMASK_SET_DOM(mask, domain) \ + ((mask)[((domain)/8)] |= (1 << (7-(domain)%8))) +#define XCPTGTMASK_DOM_IS_SET(mask, domain) \ + ((mask)[((domain)/8)] & (1 << (7-(domain)%8))) +#define XCPTGTMASK_CLR_DOM(mask, domain) \ + ((mask)[((domain)/8)] &= ~(1 << (7-(domain)%8))) + + +/* flags that can be set for the target tokens + * + * This flags are domain specific and are therefore called domain flags + * + * start of flags is >16 Bit. Max value for domains is 0xFF. Should be enough + * room for extensions + */ +#define XCP_TGTFL_WCAP 0x10000000 /* Capture wire request in output buffer + * without sending it to the module + */ +#define XCP_TGTFL_WCAP_SQ 0x20000000 /* Size query: Return size of request in + * output buffer length field + */ +#define XCP_TGTFL_SET_SCMD 0x40000000 /* Protected key special command: Set the + * special command flag in the CPRB + * header + */ +#define XCP_TGTFL_API_CHKD 0x80000000 /* supported API version of modules in + * target (group) has been checked + */ + +#define XCP_TGTFL_NO_LOCK 0x01000000 /* target token ignores sequential locks + * for target probing + */ +#define XCP_TGTFL_CHK_ATTR 0x02000000 /* reject unknown attribute in attribute + * templates with + * CKR_TEMPLATE_INCONSISTENT. Default is + * to ignore unknown attributes. + */ +#define XCP_TGTFL_SET_ACMD 0x04000000 /* add CPRB admin flag to CPRB header */ + +#define XCP_TGTFL_NO_SPLIT 0x08000000 /* enforce single-shot requests */ + +//-------------------------------------- +// socket use only +#define XCP_MAXCONNECTIONS 64 /* max value for active connections */ +#define XCP_MAX_PORT 0xffff + +// hostname and port value fore one module +typedef struct XCP_ModuleSocket { + char host[ MAX_FNAME_CHARS +1 ]; + uint32_t port; +} *XCP_ModuleSocket_t ; + + +//-------------------------------------- +// diagnostics use only +typedef struct XCP_DomainPerf { + /* perf value of last request per domain + * + * At the moment unused + * */ + unsigned int lastperf[ 256 ]; +} *XCP_DomainPerf_t; + + +// current version of XCP_Module structure; host code SHOULD interact with +// future/past versions, MUST be set by caller before using m_add_module() +// valid versions are all >0 +#define XCP_MOD_VERSION 2 +//-------------------------------------- +// subsequent communications with a module MAY skip infrastructure-specific +// fields, such as a query not reporting device handles etc., even if they +// have been supplied originally when the module has been registered. +// +typedef struct XCP_Module { + uint32_t version; /* >0 for supported API versions */ + + uint64_t flags; /* see XCP_Module_Flags */ + + uint32_t domains; /* max# addressable under this module; + * cached from OS + * + * when callers set domains to 0, the library + * returns the module-claimed domain count. + */ + + unsigned char domainmask[ 256 /8 ]; + /* higher domain# through future flags (none + * currently defined) which would add things + * like 'FLAG_256_1023' etc. at the same time, + * we would add domainmask2[] etc. + * corresponding new fields. + * + * new fields would then store mask for + * domains 256+ etc. + * + * domain #0 is bit x80 of 1st byte, + * #255 is bit 0x01 of last byte. + */ + + // when a domainmask is supplied, with bits set beyond + // what the module supports, the bitmask is trimmed to + // the supported range, but this is NOT reported as an + // error, unless XCP_MFL_STRICT is also supplied. + // + // without XCP_MFL_STRICT, callers are expected to check + // at least the returned domain count. + + /* used only when flags includes XCP_MFL_SOCKET */ + struct XCP_ModuleSocket socket; + + /* used when system exposes modules through an + * array of transparent pipes, or similar abstraction + * (such as mainframe AP Queues, or other Linux + * 'device-minor' numbers etc.). Interpretation + * is platform-dependent. + * + * used only when flags includes XCP_MFL_MODULE + */ + uint32_t module_nr; + + /* used by systems which associate devices with + * device handles/structs/etc. persistent state. + * opaque pointer, usually a const pointer to + * such aux structs, MAY be stored here. + * + * interpretation is platform-dependent. + * used only when flags includes XCP_MFL_MHANDLE + */ + void *mhandle; + /* diagnostics use only, when XCP_MFL_PERF is set */ + struct XCP_DomainPerf perf; + //----- end of v1 fields ------------------------------------------- + + uint32_t api; /* module api version*/ + //----- end of v2 fields ------------------------------------------- +} *XCP_Module_t ; + +typedef enum { + XCP_MFL_SOCKET = 1, /* backend is socket-attached */ + XCP_MFL_MODULE = 2, /* backends identified in + array-of-modules */ + XCP_MFL_MHANDLE = 4, /* backends uses 'module handle' field */ + XCP_MFL_PERF = 8, /* performance statistics collected + * for this module, see .perf + */ + XCP_MFL_VIRTUAL = 0x10, /* queried 'target' is a load-balancer, + * other other group. + */ + XCP_MFL_STRICT = 0x20, /* enable aggressive error checking, + * see field descriptions for effect + */ + XCP_MFL_PROBE = 0x40, /* send api query to module, to check if + * target(s) can be used + */ + XCP_MFL_ALW_TGT_ADD = 0x80, /* Allows it to use a target in any + * functional and admin call without + * adding it beforehand with + * m_add_module() + */ + XCP_MFL_MAX = 0xff +} XCP_Module_Flags; + typedef uint64_t target_t; + #define XCP_TGT_INIT ~0UL + #define XCP_TGT_FMT "x%016" PRIx64 -int m_init(void); -int m_shutdown(void); + int m_add_module(XCP_Module_t module, target_t *target) ; + int m_rm_module(XCP_Module_t module, target_t target) ; + +CK_RV m_admin (unsigned char *response1, size_t *r1len, + unsigned char *response2, size_t *r2len, + const unsigned char *cmd, size_t clen, + const unsigned char *sigs, size_t slen, + target_t target) ; + /*---------------------------------------------------------------------- * CK_... type arguments correspond to the original PKCS#11 call's * arguments. Standard types mean PKCS#11 objects (session, token etc.) @@ -1556,11 +2728,31 @@ * For certain operations, such as _GenerateKey, there are no real * PKCS#11 type parameters at this level. */ + + +CK_RV m_Login ( CK_UTF8CHAR_PTR pin, CK_ULONG pinlen, + const unsigned char *nonce, size_t nlen, + unsigned char *pinblob, size_t *pinbloblen, + target_t target) ; +CK_RV m_Logout ( const unsigned char *pin, size_t len, target_t target) ; + +CK_RV m_LoginExtended( CK_UTF8CHAR_PTR pin, CK_ULONG pinlen, + const unsigned char *nonce, size_t nlen, + const unsigned char *xstruct, size_t xslen, + unsigned char *pinblob, size_t *pinbloblen, + target_t target) ; + +CK_RV m_LogoutExtended( CK_UTF8CHAR_PTR pin, CK_ULONG pinlen, + const unsigned char *nonce, size_t nlen, + const unsigned char *xstruct, size_t xslen, + target_t target) ; + CK_RV m_GenerateRandom (CK_BYTE_PTR rnd, CK_ULONG len, target_t target) ; /**/ /* note: external seeding not supported */ CK_RV m_SeedRandom (CK_BYTE_PTR pSeed, CK_ULONG ulSeedLen, target_t target) ; + CK_RV m_DigestInit (unsigned char *state, size_t *len, const CK_MECHANISM_PTR pmech, target_t target) ; @@ -1582,6 +2774,74 @@ CK_BYTE_PTR data, CK_ULONG len, CK_BYTE_PTR digest, CK_ULONG_PTR dlen, target_t target) ; + +CK_RV m_GenerateKey (CK_MECHANISM_PTR pmech, + CK_ATTRIBUTE_PTR ptempl, CK_ULONG templcount, + const unsigned char *pin, size_t pinlen, + unsigned char *key, size_t *klen, + unsigned char *csum, size_t *clen, + target_t target) ; +/**/ +CK_RV m_GenerateKeyPair (CK_MECHANISM_PTR pmech, + CK_ATTRIBUTE_PTR ppublic, CK_ULONG pubattrs, + CK_ATTRIBUTE_PTR pprivate, CK_ULONG prvattrs, + const unsigned char *pin, size_t pinlen, + unsigned char *key, size_t *klen, + unsigned char *pubkey, size_t *pklen, + target_t target) ; + +/* mackey is NULL for PKCS#11 formats, not for authenticated ones */ +CK_RV m_WrapKey (const unsigned char *key, size_t keylen, + const unsigned char *kek, size_t keklen, + const unsigned char *mackey, size_t mklen, + const CK_MECHANISM_PTR pmech, + CK_BYTE_PTR wrapped, CK_ULONG_PTR wlen, + target_t target) ; +/**/ +/* mackey is NULL for PKCS#11 formats, not for authenticated ones */ +CK_RV m_UnwrapKey (const CK_BYTE_PTR wrapped, CK_ULONG wlen, + const unsigned char *kek, size_t keklen, + const unsigned char *mackey, size_t mklen, + const unsigned char *pin, size_t pinlen, + const CK_MECHANISM_PTR uwmech, + const CK_ATTRIBUTE_PTR ptempl, CK_ULONG pcount, + unsigned char *unwrapped, size_t *uwlen, + CK_BYTE_PTR csum, CK_ULONG *cslen, + target_t target) ; + +CK_RV m_DeriveKey ( CK_MECHANISM_PTR pderivemech, + CK_ATTRIBUTE_PTR ptempl, CK_ULONG templcount, + const unsigned char *basekey, size_t bklen, + const unsigned char *data, size_t dlen, + const unsigned char *pin, size_t pinlen, + unsigned char *newkey, size_t *nklen, + unsigned char *csum, size_t *cslen, + target_t target) ; + +CK_RV m_GetAttributeValue (const unsigned char *obj, size_t olen, + CK_ATTRIBUTE_PTR pTemplate, CK_ULONG ulCount, + target_t target) ; +CK_RV m_SetAttributeValue (unsigned char *obj, size_t olen, + CK_ATTRIBUTE_PTR pTemplate, CK_ULONG ulCount, + target_t target) ; + +/**/ +CK_RV m_GetMechanismList (CK_SLOT_ID slot, + CK_MECHANISM_TYPE_PTR mechs, + CK_ULONG_PTR count, + target_t target) ; +CK_RV m_GetMechanismInfo (CK_SLOT_ID slot, + CK_MECHANISM_TYPE mech, + CK_MECHANISM_INFO_PTR pmechinfo, + target_t target) ; + +CK_RV m_get_xcp_info (CK_VOID_PTR pinfo, CK_ULONG_PTR infbytes, + unsigned int query, + unsigned int subquery, + target_t target) ; + +// see also: CK_IBM_XCPQUERY_t + CK_RV m_EncryptInit (unsigned char *state, size_t *slen, CK_MECHANISM_PTR pmech, const unsigned char *key, size_t klen, @@ -1628,20 +2888,7 @@ CK_BYTE_PTR cipher, CK_ULONG clen, CK_BYTE_PTR plain, CK_ULONG_PTR plen, target_t target) ; -CK_RV m_GenerateKey (CK_MECHANISM_PTR pmech, - CK_ATTRIBUTE_PTR ptempl, CK_ULONG templcount, - const unsigned char *pin, size_t pinlen, - unsigned char *key, size_t *klen, - unsigned char *csum, size_t *clen, - target_t target) ; -/**/ -CK_RV m_GenerateKeyPair (CK_MECHANISM_PTR pmech, - CK_ATTRIBUTE_PTR ppublic, CK_ULONG pubattrs, - CK_ATTRIBUTE_PTR pprivate, CK_ULONG prvattrs, - const unsigned char *pin, size_t pinlen, - unsigned char *key, size_t *klen, - unsigned char *pubkey, size_t *pklen, - target_t target) ; + CK_RV m_SignInit (unsigned char *state, size_t *slen, CK_MECHANISM_PTR alg, const unsigned char *key, size_t klen, @@ -1684,66 +2931,16 @@ CK_BYTE_PTR data, CK_ULONG dlen, CK_BYTE_PTR sig, CK_ULONG slen, target_t target) ; -/* mackey is NULL for PKCS#11 formats, not for authenticated ones */ -CK_RV m_WrapKey (const unsigned char *key, size_t keylen, - const unsigned char *kek, size_t keklen, - const unsigned char *mackey, size_t mklen, - const CK_MECHANISM_PTR pmech, - CK_BYTE_PTR wrapped, CK_ULONG_PTR wlen, - target_t target) ; -/**/ -/* mackey is NULL for PKCS#11 formats, not for authenticated ones */ -CK_RV m_UnwrapKey (const CK_BYTE_PTR wrapped, CK_ULONG wlen, - const unsigned char *kek, size_t keklen, - const unsigned char *mackey, size_t mklen, - const unsigned char *pin, size_t pinlen, - const CK_MECHANISM_PTR uwmech, - const CK_ATTRIBUTE_PTR ptempl, CK_ULONG pcount, - unsigned char *unwrapped, size_t *uwlen, - CK_BYTE_PTR csum, CK_ULONG *cslen, - target_t target) ; -CK_RV m_DeriveKey ( CK_MECHANISM_PTR pderivemech, - CK_ATTRIBUTE_PTR ptempl, CK_ULONG templcount, - const unsigned char *basekey, size_t bklen, - const unsigned char *data, size_t dlen, - const unsigned char *pin, size_t pinlen, - unsigned char *newkey, size_t *nklen, - unsigned char *csum, size_t *cslen, - target_t target) ; -/**/ -CK_RV m_GetMechanismList (CK_SLOT_ID slot, - CK_MECHANISM_TYPE_PTR mechs, - CK_ULONG_PTR count, - target_t target) ; -CK_RV m_GetMechanismInfo (CK_SLOT_ID slot, - CK_MECHANISM_TYPE mech, - CK_MECHANISM_INFO_PTR pmechinfo, - target_t target) ; -CK_RV m_GetAttributeValue (const unsigned char *obj, size_t olen, - CK_ATTRIBUTE_PTR pTemplate, CK_ULONG ulCount, - target_t target) ; -CK_RV m_SetAttributeValue (unsigned char *obj, size_t olen, - CK_ATTRIBUTE_PTR pTemplate, CK_ULONG ulCount, - target_t target) ; -CK_RV m_Login ( CK_UTF8CHAR_PTR pin, CK_ULONG pinlen, - const unsigned char *nonce, size_t nlen, - unsigned char *pinblob, size_t *pinbloblen, - target_t target) ; -CK_RV m_Logout ( const unsigned char *pin, size_t len, target_t target) ; -CK_RV m_admin (unsigned char *response1, size_t *r1len, - unsigned char *response2, size_t *r2len, - const unsigned char *cmd, size_t clen, - const unsigned char *sigs, size_t slen, - target_t target) ; -CK_RV m_get_xcp_info (CK_VOID_PTR pinfo, CK_ULONG_PTR infbytes, - unsigned int query, - unsigned int subquery, - target_t target) ; + +// m_wire() by default removes transport headers of responses (CPRB header etc.) +// setting to prevent stripping: +// #define XCP_CHN_RETURN_RAW 1 /* return raw wire response, w/headers */ #define XCP_CHN_HIGH_PRIORITY 2 /* please note: Not all backends */ #define XCP_CHN_MEDIUM_PRIORITY 4 /* support channel priority mgmt */ #define XCP_CHN_NODEV_LOG_SKIP 8 /* do not log if no device is found */ #define XCP_CHN_PARSE_IRV 0x10 + /*-------------------------------------------------------------------------- * direct interface without wire formatting & parsing. */ @@ -1751,15 +2948,28 @@ const unsigned char *req, size_t reqlen, unsigned int flags, target_t target) ; + +// options allowed within flags #define XCP_W_NO_SEND_CPRB 1 /* data already includes request header */ #define XCP_W_NO_RECV_CPRB 2 /* leave transport header in response */ + +// initializes the library +int m_init(void); +// shutting down the library +int m_shutdown(void); + + + /*-- build identification ------------------------------------------------*/ -#define XCP_BUILD_ID 0xba1d9ae2 -#define XCP_BUILD_DATE 0x20200211 /* UTC */ -#define XCP_BUILD_TIME 0x080208 /* UTC */ -/*--------------------------------------------------------------------------*/ + +#define XCP_BUILD_ID 0xf1d34cc2 +#define XCP_BUILD_DATE 0x20221214 /* UTC */ +#define XCP_BUILD_TIME 0x094523 /* UTC */ + /*--------------------------------------------------------------------------*/ #define __XCP_REASONCODES_H__ 1 + + typedef enum { XCP_RSC_NO_IMPORTER = 1, /* targeted domain has no importer private key */ XCP_RSC_NO_KEYPARTS = 2, /* import WK request without keypart SEQUENCEs */ @@ -1891,13 +3101,28 @@ XCP_RSC_IMPR_IMPORT_TGT_DOM_ZEROIZE_FAILED = 128, /* import: zeroize of target domain failed */ XCP_RSC_AUDIT_QUERY_PAYLOAD_SIZE = 129, /* audit query: size of payload too small */ XCP_RSC_AUDIT_QUERY_INVALID_INDEX = 130, /* audit query: invalid audit history index */ - XCP_RSC_MAX = XCP_RSC_AUDIT_QUERY_INVALID_INDEX + XCP_RSC_EXPORT_WK_PROHIBITED = 131, /* export of WKs prohibited by policy */ + XCP_RSC_EXPORT_STATE_PROHIBITED = 132, /* export of state prohibited by policy */ + XCP_RSC_IMPORT_STATE_PROHIBITED = 133, /* import of state prohibited by policy */ + XCP_RSC_EXPORT_WK_UNAUTHORIZED = 134, /* Card admin attempted to export a DnD domain WK (empty dom admin exp.request?) */ + XCP_RSC_OA_SIG_POLICY_VIOLATION = 135, /* invalid OA signature config, at least one OA signature type must be enabled */ + XCP_RSC_OA_SIG_NOT_SUPPORTED = 136, /* requested OA signature type not supported/configured */ + XCP_RSC_ASN_FMT_INVALID = 137, /* invalid ASN.1 encoded format */ + XCP_RSC_CERT_TYPE_INVALID = 138, /* Certificate type invalid */ + XCP_RSC_ROLE_ID_INVALID = 139, /* Role ID invalid */ + XCP_RSC_ADM_SIG_POLICY_VIOLATION = 140, /* invalid ADM signature config, at least one ADM signature type must be enabled */ + XCP_RSC_KEY_STRENGTH_POLICY_VIOLATION = 141, /* invalid key strength configuration, a maximum of only one bit may be enabled */ + XCP_RSC_ADM_SIG_CHANGE_PROHIBITED = 142, /* ADM signature configuration change prohibited, not enough remaining admins to meet security */ + XCP_RSC_KEY_STRENGTH_CHANGE_PROHIBITED = 143, /* Key strength configuration change prohibited, not enough remaining admins to meet security */ + XCP_RSC_MAX = XCP_RSC_KEY_STRENGTH_CHANGE_PROHIBITED } XCP_ReasonCode_t ; -#if ! defined(__transport_fns_h__) -#define __transport_fns_h__ + + /* function identifiers must be consecutive, between: */ #define __MIN_MOD_FNID 1 -#define __MAX_MOD_FNID 43 +#define __MAX_MOD_FNID 42 +/* selectively disabled functions within that range reported separately */ + #define __FNID_Login 1 #define __FNID_Logout 2 #define __FNID_SeedRandom 3 @@ -1940,10 +3165,70 @@ #define __FNID_SetAttributeValue 40 #define __FNID_admin 41 #define __FNID_ReencryptSingle 42 +// #define __FNID_NEXT_AVAILABLE 43 +// #define __FNID_MAX __FNID_ReencryptSingle + + +// +// 64 bit mask. See XCP__FNIDS_DW1 if more bits required (up to 128 bit) +#define XCP__FNIDS_BIT0 0x8000000000000000ULL +#define XCP__FNIDS_DW0 \ + ( (XCP__FNIDS_BIT0) |\ + (XCP__FNIDS_BIT0 >> __FNID_Login) |\ + (XCP__FNIDS_BIT0 >> __FNID_Logout) |\ + (XCP__FNIDS_BIT0 >> __FNID_SeedRandom) |\ + (XCP__FNIDS_BIT0 >> __FNID_GenerateRandom) |\ + (XCP__FNIDS_BIT0 >> __FNID_DigestInit) |\ + (XCP__FNIDS_BIT0 >> __FNID_DigestUpdate) |\ +/*NOTE: FNID_DigestKey is not supported \ + (XCP__FNIDS_BIT0 >> __FNID_DigestKey) |\ +*/ \ + (XCP__FNIDS_BIT0 >> __FNID_DigestFinal) |\ + (XCP__FNIDS_BIT0 >> __FNID_Digest) |\ + (XCP__FNIDS_BIT0 >> __FNID_DigestSingle) |\ + (XCP__FNIDS_BIT0 >> __FNID_EncryptInit) |\ + (XCP__FNIDS_BIT0 >> __FNID_DecryptInit) |\ + (XCP__FNIDS_BIT0 >> __FNID_EncryptUpdate) |\ + (XCP__FNIDS_BIT0 >> __FNID_DecryptUpdate) |\ + (XCP__FNIDS_BIT0 >> __FNID_EncryptFinal) |\ + (XCP__FNIDS_BIT0 >> __FNID_DecryptFinal) |\ + (XCP__FNIDS_BIT0 >> __FNID_Encrypt) |\ + (XCP__FNIDS_BIT0 >> __FNID_Decrypt) |\ + (XCP__FNIDS_BIT0 >> __FNID_EncryptSingle) |\ + (XCP__FNIDS_BIT0 >> __FNID_DecryptSingle) |\ + (XCP__FNIDS_BIT0 >> __FNID_GenerateKey) |\ + (XCP__FNIDS_BIT0 >> __FNID_GenerateKeyPair) |\ + (XCP__FNIDS_BIT0 >> __FNID_SignInit) |\ + (XCP__FNIDS_BIT0 >> __FNID_SignUpdate) |\ + (XCP__FNIDS_BIT0 >> __FNID_SignFinal) |\ + (XCP__FNIDS_BIT0 >> __FNID_Sign) |\ + (XCP__FNIDS_BIT0 >> __FNID_VerifyInit) |\ + (XCP__FNIDS_BIT0 >> __FNID_VerifyUpdate) |\ + (XCP__FNIDS_BIT0 >> __FNID_VerifyFinal) |\ + (XCP__FNIDS_BIT0 >> __FNID_Verify) |\ + (XCP__FNIDS_BIT0 >> __FNID_SignSingle) |\ + (XCP__FNIDS_BIT0 >> __FNID_VerifySingle) |\ + (XCP__FNIDS_BIT0 >> __FNID_WrapKey) |\ + (XCP__FNIDS_BIT0 >> __FNID_UnwrapKey) |\ + (XCP__FNIDS_BIT0 >> __FNID_DeriveKey) |\ + (XCP__FNIDS_BIT0 >> __FNID_GetMechanismList) |\ + (XCP__FNIDS_BIT0 >> __FNID_GetMechanismInfo) |\ + (XCP__FNIDS_BIT0 >> __FNID_get_xcp_info) |\ + (XCP__FNIDS_BIT0 >> __FNID_GetAttributeValue) |\ + (XCP__FNIDS_BIT0 >> __FNID_SetAttributeValue) |\ + (XCP__FNIDS_BIT0 >> __FNID_admin) |\ + (XCP__FNIDS_BIT0 >> __FNID_ReencryptSingle)) + +// used for the module query, see CK_IBM_XCPMSQ_FNLIST +#define XCP__FNIDS_DW1 0 + + /* maximum nr of non-system parameters: */ #define __HOST2MOD_DATAPRM 9 #define __MOD2HOST_DATAPRM 2 -#endif /* n defined(__transport_fns_h__) */ + + #endif /* n defined(XCP_H__) */ + diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11_specific.c opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11_specific.c --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11_specific.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11_specific.c 2023-02-13 09:22:42.000000000 +0100 @@ -37,13 +37,15 @@ #include "trace.h" #include "ock_syslog.h" #include "ec_defs.h" +#include "pqc_defs.h" #include "p11util.h" #include "events.h" +#include "cfgparser.h" +#include "configuration.h" #include #include #include -#include #include #include #include @@ -64,6 +66,7 @@ #include "pkey_utils.h" #define EP11SHAREDLIB_NAME "OCK_EP11_LIBRARY" +#define EP11SHAREDLIB_V4 "libep11.so.4" #define EP11SHAREDLIB_V3 "libep11.so.3" #define EP11SHAREDLIB_V2 "libep11.so.2" #define EP11SHAREDLIB_V1 "libep11.so.1" @@ -154,9 +157,10 @@ #define MAX_CSUMSIZE 64 #define EP11_CSUMSIZE 3 #define MAX_DIGEST_STATE_BYTES 1024 -#define MAX_CRYPT_STATE_BYTES 8192 -#define MAX_SIGN_STATE_BYTES 8192 +#define MAX_CRYPT_STATE_BYTES 12288 +#define MAX_SIGN_STATE_BYTES 12288 #define MAX_APQN 256 +#define EP11_BLOB_WKID_OFFSET 32 /* wrap_key is used for importing keys */ static const char wrap_key_name[] = "EP11_wrapkey"; @@ -203,10 +207,20 @@ do { \ int retry_count; \ CK_RV rc2; \ + if (((ep11_private_data_t *) \ + tokdata->private_data)-> \ + inconsistent) { \ + (rc) = CKR_DEVICE_ERROR; \ + TRACE_ERROR("%s\n", \ + ock_err(ERR_DEVICE_ERROR)); \ + break; \ + } \ ep11_target_info_t* target_info = \ get_target_info((tokdata)); \ - if (target_info == NULL) \ + if (target_info == NULL) { \ (rc) = CKR_FUNCTION_FAILED; \ + break; \ + } \ for(retry_count = 0; \ target_info != NULL && \ retry_count < MAX_RETRY_COUNT; \ @@ -234,7 +248,10 @@ static CK_RV ep11_open_helper_session(STDLL_TokData_t * tokdata, SESSION * sess, CK_SESSION_HANDLE_PTR phSession); static CK_RV ep11_close_helper_session(STDLL_TokData_t * tokdata, - ST_SESSION_HANDLE * sSession); + ST_SESSION_HANDLE * sSession, + CK_BBOOL in_fork_initializer); +static CK_RV ep11_login_handler(uint_32 adapter, uint_32 domain, + void *handler_data); static CK_BBOOL ep11tok_ec_curve_supported2(STDLL_TokData_t *tokdata, TEMPLATE *template, @@ -344,6 +361,13 @@ }; #define NUM_DILITHIUM_REQ (sizeof(ibm_dilithium_req_versions) / sizeof(version_req_t)) +static const CK_VERSION ibm_cex8p_kyber_support = { .major = 8, .minor = 9 }; + +static const version_req_t ibm_kyber_req_versions[] = { + { .card_type = 8, .min_firmware_version = &ibm_cex8p_kyber_support } +}; +#define NUM_KYBER_REQ (sizeof(ibm_kyber_req_versions) / sizeof(version_req_t)) + static const CK_VERSION ibm_cex6p_reencrypt_single_support = { .major = 6, .minor = 15 }; static const CK_VERSION ibm_cex7p_reencrypt_single_support = @@ -370,6 +394,29 @@ }; #define NUM_AB_ECDH_REQ (sizeof(ibm_ab_ecdh_req_versions) / sizeof(version_req_t)) +static const CK_VERSION ibm_cex6p_btc_support = { .major = 6, .minor = 15 }; +static const CK_VERSION ibm_cex7p_btc_support = { .major = 7, .minor = 21 }; + +static const version_req_t ibm_btc_req_versions[] = { + { .card_type = 6, .min_firmware_version = &ibm_cex6p_btc_support }, + { .card_type = 7, .min_firmware_version = &ibm_cex7p_btc_support } +}; +#define NUM_BTC_REQ (sizeof(ibm_btc_req_versions) / sizeof(version_req_t)) + +static const CK_VERSION ibm_cex6p_ecdsa_other_support = + { .major = 6, .minor = 15 }; +static const CK_VERSION ibm_cex7p_ecdsa_other_support = + { .major = 7, .minor = 21 }; + +static const version_req_t ibm_ecdsa_other_req_versions[] = { + { .card_type = 6, .min_firmware_version = + &ibm_cex6p_ecdsa_other_support }, + { .card_type = 7, .min_firmware_version = + &ibm_cex7p_ecdsa_other_support } +}; +#define NUM_ECDSA_OTHER_REQ (sizeof(ibm_ecdsa_other_req_versions) / \ + sizeof(version_req_t)) + /* Definitions for loading libica dynamically */ typedef unsigned int (*ica_sha1_t)(unsigned int message_part, @@ -440,6 +487,7 @@ unsigned char *output_data); #endif typedef void (*ica_cleanup_t) (void); +typedef int (*ica_fips_status_t) (void); typedef struct { CK_BYTE buffer[MAX_SHA_BLOCK_SIZE]; @@ -475,6 +523,7 @@ ica_sha3_512_t ica_sha3_512; #endif ica_cleanup_t ica_cleanup; + ica_fips_status_t ica_fips_status; } libica_t; /* target list of adapters/domains, specified in a config file by user, @@ -497,6 +546,11 @@ #define PKEY_MODE_DEFAULT 1 #define PKEY_MODE_ENABLE4NONEXTR 2 +#define PQC_BYTE_NO(idx) (((idx) - 1) / 8) +#define PQC_BIT_IN_BYTE(idx) (((idx - 1)) % 8) +#define PQC_BIT_MASK(idx) (0x80 >> PQC_BIT_IN_BYTE(idx)) +#define PQC_BYTES ((((XCP_PQC_MAX / 32) * 32) + 32) / 8) + typedef struct { volatile unsigned long ref_count; target_t target; @@ -506,6 +560,7 @@ size_t control_points_len; size_t max_control_point_index; CK_CHAR serialNumber[16]; + CK_BYTE pqc_strength[PQC_BYTES]; } ep11_target_info_t; typedef struct { @@ -524,6 +579,9 @@ int msa_level; int digest_libica; char digest_libica_path[PATH_MAX]; + unsigned char expected_wkvp[XCP_WKID_BYTES]; + int expected_wkvp_set; + int inconsistent; libica_t libica; void *lib_ep11; CK_VERSION ep11_lib_version; @@ -540,7 +598,8 @@ target_t *target, uint64_t flags); static void free_ep11_target_for_apqn(target_t target); static CK_RV update_ep11_attrs_from_blob(STDLL_TokData_t *tokdata, - TEMPLATE *tmpl); + SESSION *session, TEMPLATE *tmpl, + CK_BBOOL aes_xts); /* defined in the makefile, ep11 library can run standalone (without HW card), @@ -588,17 +647,131 @@ return CKR_OK; } +static CK_RV check_expected_mkvp(STDLL_TokData_t *tokdata, CK_BYTE *blob, + size_t blobsize) +{ + ep11_private_data_t *ep11_data = tokdata->private_data; + + if (blobsize < EP11_BLOB_WKID_OFFSET + XCP_WKID_BYTES) { + TRACE_ERROR("EP11 key blob is too small\n"); + return CKR_FUNCTION_FAILED; + } + + if (memcmp(blob + EP11_BLOB_WKID_OFFSET, ep11_data->expected_wkvp, + XCP_WKID_BYTES) != 0) { + TRACE_ERROR("The key's wrapping key verification pattern does not " + "match the expected EP11 wrapping key\n"); + TRACE_DEBUG_DUMP("WKVP of key: ", blob + EP11_BLOB_WKID_OFFSET, + XCP_WKID_BYTES); + TRACE_DEBUG_DUMP("Expected WKVP: ", (CK_BYTE *)ep11_data->expected_wkvp, + XCP_WKID_BYTES); + OCK_SYSLOG(LOG_ERR, "The key's wrapping key verification pattern does " + "not match the expected EP11 wrapping key\n"); + return CKR_DEVICE_ERROR; + } + + return CKR_OK; +} + +static CK_BBOOL ep11_pqc_strength_supported(ep11_target_info_t *target_info, + CK_MECHANISM_TYPE mech, + const struct pqc_oid *oid) +{ + CK_ULONG strength; + + switch (mech) { + case CKM_IBM_DILITHIUM: + switch (oid->keyform) { + case CK_IBM_DILITHIUM_KEYFORM_ROUND2_65: + strength = XCP_PQC_S_DILITHIUM_R2_65; + break; + case CK_IBM_DILITHIUM_KEYFORM_ROUND2_87: + strength = XCP_PQC_S_DILITHIUM_R2_87; + break; + case CK_IBM_DILITHIUM_KEYFORM_ROUND3_44: + strength = XCP_PQC_S_DILITHIUM_R3_44; + break; + case CK_IBM_DILITHIUM_KEYFORM_ROUND3_65: + strength = XCP_PQC_S_DILITHIUM_R3_65; + break; + case CK_IBM_DILITHIUM_KEYFORM_ROUND3_87: + strength = XCP_PQC_S_DILITHIUM_R3_87; + break; + default: + TRACE_DEVEL("Dilithium keyform %lu not supported by EP11\n", + oid->keyform); + return FALSE; + } + break; + case CKM_IBM_KYBER: + switch (oid->keyform) { + case CK_IBM_KYBER_KEYFORM_ROUND2_768: + strength = XCP_PQC_S_KYBER_R2_768; + break; + case CK_IBM_KYBER_KEYFORM_ROUND2_1024: + strength = XCP_PQC_S_KYBER_R2_1024; + break; + default: + TRACE_DEVEL("Kyber keyform %lu not supported by EP11\n", + oid->keyform); + return FALSE; + } + break; + default: + return FALSE; + } + + if ((target_info->pqc_strength[PQC_BYTE_NO(strength)] & + PQC_BIT_MASK(strength)) == 0) { + TRACE_DEVEL("Keyform %lu not supported by configured APQNs\n", + oid->keyform); + return FALSE; + } + + return TRUE; +} + +static CK_BBOOL ep11_pqc_obj_strength_supported(ep11_target_info_t *target_info, + CK_MECHANISM_TYPE mech, + OBJECT *key_obj) +{ + const struct pqc_oid *oid; + + switch (mech) { + case CKM_IBM_DILITHIUM: + case CKM_IBM_KYBER: + break; + default: + return TRUE; + } + + oid = ibm_pqc_get_keyform_mode(key_obj->template, mech); + if (oid == NULL) { + TRACE_DEVEL("No keyform/mode found in key object\n"); + return FALSE; + } + + return ep11_pqc_strength_supported(target_info, mech, oid); +} + /******************************************************************************* * * Begin EP11 protected key option */ typedef struct { + ep11_session_t *ep11_session; CK_BBOOL wrap_was_successful; CK_VOID_PTR secure_key; CK_ULONG secure_key_len; CK_BYTE *pkey_buf; size_t *pkey_buflen_p; + /* for AES XTS processing */ + CK_VOID_PTR secure_key2; + CK_ULONG secure_key_len2; + CK_BYTE *pkey_buf2; + size_t *pkey_buflen_p2; + CK_BBOOL aes_xts; } pkey_wrap_handler_data_t; /* A wrapped key can have max 132 bytes for an EC-p521 key */ @@ -639,6 +812,7 @@ pkey_wrap_handler_data_t *data = (pkey_wrap_handler_data_t *) handler_data; target_t target = 0; CK_RV ret; + CK_BBOOL retry = FALSE; if (data->wrap_was_successful) goto done; @@ -648,10 +822,40 @@ goto done; /* Create the protected key via CKM_IBM_CPACF_WRAP */ +repeat: ret = dll_m_WrapKey(data->secure_key, data->secure_key_len, NULL, 0, NULL, 0, &mech, data->pkey_buf, data->pkey_buflen_p, target | XCP_TGTFL_SET_SCMD); + if (ret == CKR_SESSION_CLOSED && retry == FALSE && + data->ep11_session != NULL) { + /* Re-login the EP11 session and retry once */ + ret = ep11_login_handler(adapter, domain, data->ep11_session); + if (ret == CKR_OK) { + retry = TRUE; + goto repeat; + } + } + + if (data->aes_xts && ret == CKR_OK) { + /* Create the protected key via CKM_IBM_CPACF_WRAP */ + retry = FALSE; +repeat2: + ret = dll_m_WrapKey(data->secure_key2, data->secure_key_len2, + NULL, 0, NULL, 0, &mech, + data->pkey_buf2, data->pkey_buflen_p2, + target | XCP_TGTFL_SET_SCMD); + if (ret == CKR_SESSION_CLOSED && retry == FALSE && + data->ep11_session != NULL) { + /* Re-login the EP11 session and retry once */ + ret = ep11_login_handler(adapter, domain, data->ep11_session); + if (ret == CKR_OK) { + retry = TRUE; + goto repeat2; + } + } + } + if (ret == CKR_OK) data->wrap_was_successful = CK_TRUE; @@ -668,26 +872,45 @@ * Creates a protected key from the given secure key object via the ep11 lib * CKM_IBM_CPACF_WRAP mechanism. */ -static CK_RV ep11tok_pkey_skey2pkey(STDLL_TokData_t *tokdata, +static CK_RV ep11tok_pkey_skey2pkey(STDLL_TokData_t *tokdata, SESSION *session, CK_ATTRIBUTE *skey_attr, - CK_ATTRIBUTE **pkey_attr) + CK_ATTRIBUTE **pkey_attr, CK_BBOOL aes_xts) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_ATTRIBUTE *tmp_attr = NULL; CK_BYTE ep11_buf[sizeof(wrapped_key_t)]; size_t ep11_buflen = sizeof(ep11_buf); + CK_BYTE ep11_buf2[sizeof(wrapped_key_t)]; + size_t ep11_buflen2 = sizeof(ep11_buf2); pkey_wrap_handler_data_t pkey_wrap_handler_data; - wrapped_key_t *wk; + wrapped_key_t *wk, *wk2; + uint64_t token_size = 0; + uint8_t wrapped_key[EP11_MAX_WRAPPED_KEY_SIZE * 2]; CK_RV ret; /* Create the protected key via CKM_IBM_CPACF_WRAP */ memset(&pkey_wrap_handler_data, 0, sizeof(pkey_wrap_handler_data_t)); + if (session != NULL) + pkey_wrap_handler_data.ep11_session = + (ep11_session_t *)session->private_data; pkey_wrap_handler_data.secure_key = skey_attr->pValue; pkey_wrap_handler_data.secure_key_len = skey_attr->ulValueLen; pkey_wrap_handler_data.pkey_buf = (CK_BYTE *)&ep11_buf; pkey_wrap_handler_data.pkey_buflen_p = &ep11_buflen; - ret = handle_all_ep11_cards(&ep11_data->target_list, ep11tok_pkey_wrap_handler, - &pkey_wrap_handler_data); + pkey_wrap_handler_data.aes_xts = FALSE; + + if (aes_xts) { + pkey_wrap_handler_data.secure_key_len = skey_attr->ulValueLen / 2; + pkey_wrap_handler_data.secure_key2 = (CK_BYTE *)skey_attr->pValue + skey_attr->ulValueLen / 2; + pkey_wrap_handler_data.secure_key_len2 = skey_attr->ulValueLen / 2; + pkey_wrap_handler_data.pkey_buf2 = (CK_BYTE *)&ep11_buf2; + pkey_wrap_handler_data.pkey_buflen_p2 = &ep11_buflen2; + pkey_wrap_handler_data.aes_xts = TRUE; + } + + ret = handle_all_ep11_cards(&ep11_data->target_list, + ep11tok_pkey_wrap_handler, &pkey_wrap_handler_data); + if (ret != CKR_OK || !pkey_wrap_handler_data.wrap_was_successful) { TRACE_ERROR("handle_all_ep11_cards failed or no APQN could do the wrap.\n"); ret = CKR_FUNCTION_FAILED; @@ -720,9 +943,52 @@ goto done; } + if (wk->token_size > sizeof(wrapped_key)) { + TRACE_ERROR("Buffer too small\n"); + ret = CKR_BUFFER_TOO_SMALL; + goto done; + } + + token_size = wk->token_size; + /* copy wrapped key to wrapped_key variable to create CKA_IBM_OPAQUE_PKEY */ + memcpy(wrapped_key, wk->wrapped_key, wk->token_size); + + if (aes_xts) { + /* Check ep11 wrapped key struct version and length. We currently only + * support/expect version 0x0001 structs. */ + wk2 = (wrapped_key_t *) &ep11_buf2; + if (ep11_buflen2 != sizeof(wrapped_key_t) || + wk2->version != EP11_WRAPPED_KEY_VERSION_1) { + TRACE_ERROR("invalid ep11 wrapped key struct length %ld\n", ep11_buflen2); + ret = CKR_FUNCTION_FAILED; + goto done; + } + /* Check if returned key type is what we expect: + * - 0x1 = AES with bit length 128 and 256 + */ + switch (wk2->wrapped_key_type) { + case EP11_WRAPPED_KEY_TYPE_AES: + break; + default: + TRACE_ERROR("Got unexpected CPACF key type %d from firmware\n", + wk->wrapped_key_type); + ret = CKR_FUNCTION_FAILED; + goto done; + } + + if (wk2->token_size > sizeof(wrapped_key) - wk->token_size) { + TRACE_ERROR("Wrapped key size too big\n"); + ret = CKR_BUFFER_TOO_SMALL; + goto done; + } + + token_size += wk2->token_size; + memcpy(wrapped_key + wk->token_size, wk2->wrapped_key, wk2->token_size); + } + /* Build new attribute for protected key */ - ret = build_attribute(CKA_IBM_OPAQUE_PKEY, wk->wrapped_key, - wk->token_size, &tmp_attr); + ret = build_attribute(CKA_IBM_OPAQUE_PKEY, wrapped_key, + token_size, &tmp_attr); if (ret != CKR_OK) { TRACE_ERROR("build_attribute failed with rc=0x%lx\n", ret); ret = CKR_FUNCTION_FAILED;; @@ -785,6 +1051,12 @@ goto done; } + if (check_expected_mkvp(tokdata, blob, blobsize) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + ret = CKR_DEVICE_ERROR; + goto done; + } + /* Build attribute for secure key blob */ ret = build_attribute(CKA_IBM_OPAQUE, blob, blobsize, &blob_attr); if (ret != CKR_OK) { @@ -795,7 +1067,7 @@ /* Create a protected key from this blob to obtain the LPAR MK vp. When * this function returns ok, we have a 64 byte pkey value: 32 bytes * encrypted key + 32 bytes vp. */ - ret = ep11tok_pkey_skey2pkey(tokdata, blob_attr, &pkey_attr); + ret = ep11tok_pkey_skey2pkey(tokdata, NULL, blob_attr, &pkey_attr, FALSE); if (ret != CKR_OK) { TRACE_ERROR("ep11tok_pkey_skey2pkey failed with rc=0x%lx\n", ret); goto done; @@ -861,7 +1133,8 @@ * Create a new protected key for the given key obj and update attribute * CKA_IBM_OPAQUE with the new pkey. */ -static CK_RV ep11tok_pkey_update(STDLL_TokData_t *tokdata, OBJECT *key_obj) +static CK_RV ep11tok_pkey_update(STDLL_TokData_t *tokdata, SESSION *session, + OBJECT *key_obj, CK_BBOOL aes_xts) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_ATTRIBUTE *skey_attr = NULL; @@ -878,7 +1151,7 @@ } /* Transform the secure key into a protected key */ - ret = ep11tok_pkey_skey2pkey(tokdata, skey_attr, &pkey_attr); + ret = ep11tok_pkey_skey2pkey(tokdata, session, skey_attr, &pkey_attr, aes_xts); if (ret != CKR_OK) { TRACE_ERROR("protected key creation failed with rc=0x%lx\n",ret); goto done; @@ -895,6 +1168,21 @@ goto done; } + if (aes_xts) { + /* Check if the new pkey's verification pattern matches the one in + * ep11_data. This should always be the case, because we just + * created the pkey with the current MK. + * AES XTS has two keys, two keys are concatenated. + * Second key is checked above and the first key is checked here */ + vp_offset = pkey_attr->ulValueLen / 2 - PKEY_MK_VP_LENGTH; + if (memcmp(&ep11_data->pkey_mk_vp, (CK_BYTE *)pkey_attr->pValue + vp_offset, + PKEY_MK_VP_LENGTH) != 0) { + TRACE_ERROR("vp of this pkey does not match with the one in ep11_data (should not occur)\n"); + ret = CKR_FUNCTION_FAILED; + goto done; + } + } + /* Now update the key obj. If it's a token obj, it will be also updated * in the repository. */ ret = pkey_update_and_save(tokdata, key_obj, pkey_attr); @@ -912,15 +1200,28 @@ /** * Returns true if the session is ok for creating protected keys, false - * otherwise. The session must be read/write and not public, because the - * protected key is a private/secret key attribute. + * otherwise. The session must be read/write for token objects, and not public + * nor SO for private objects. */ -static CK_BBOOL ep11tok_pkey_session_read_write(SESSION *session) +static CK_BBOOL ep11tok_pkey_session_ok_for_obj(SESSION *session, + OBJECT *key_obj) { - if (session->session_info.flags & CKF_RW_SESSION) - return CK_TRUE; + if (object_is_token_object(key_obj) && + (session->session_info.flags & CKF_RW_SESSION) == 0) + return CK_FALSE; - return CK_FALSE; + if (object_is_private(key_obj)) { + switch (session->session_info.state) { + case CKS_RO_PUBLIC_SESSION: + case CKS_RW_PUBLIC_SESSION: + case CKS_RW_SO_FUNCTIONS: + return CK_FALSE; + default: + break; + } + } + + return CK_TRUE; } /** @@ -991,19 +1292,25 @@ if (object_is_extractable(key_obj) || !object_is_pkey_extractable(key_obj) || object_is_attr_bound(key_obj) || - !ep11tok_pkey_session_read_write(session) || !ep11_data->pkey_wrap_supported) { goto done; } + if (template_attribute_get_non_empty(key_obj->template, CKA_IBM_OPAQUE_PKEY, &opaque_attr) != CKR_OK || !ep11tok_pkey_is_valid(tokdata, key_obj)) { /* this key has either no pkey attr, or it is not valid, - * try to create one */ - ret = ep11tok_pkey_update(tokdata, key_obj); + * try to create one, if the session state allows it */ + if (!ep11tok_pkey_session_ok_for_obj(session, key_obj)) + goto done; + + ret = ep11tok_pkey_update(tokdata, session, key_obj, + mech->mechanism == CKM_AES_XTS); if (ret != CKR_OK) { - TRACE_ERROR("error updating the protected key, rc=0x%lx\n", ret); + TRACE_ERROR("error updating the %s protected key, rc=0x%lx\n", + mech->mechanism == CKM_AES_XTS ? "AES XTS" : "AES", + ret); if (ret == CKR_FUNCTION_NOT_SUPPORTED) ret = CKR_FUNCTION_FAILED; goto done; @@ -1055,6 +1362,23 @@ return success; } +CK_RV ep11tok_pkey_check_aes_xts(STDLL_TokData_t *tokdata, OBJECT *key_obj, + CK_MECHANISM_TYPE type) +{ + if (ep11tok_is_mechanism_supported(tokdata, type) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_INVALID)); + return CKR_MECHANISM_INVALID; + } + + if (object_is_extractable(key_obj) || + !object_is_pkey_extractable(key_obj) || + object_is_attr_bound(key_obj)) { + return CKR_TEMPLATE_INCONSISTENT; + } + + return CKR_OK; +} + /** * This function is called whenever a new object is created. It currently sets * attribute CKA_IBM_PROTKEY_EXTRACTABLE according to the PKEY_MODE token @@ -1117,6 +1441,7 @@ ret = template_update_attribute(tmpl, pkey_attr); if (ret != CKR_OK) { TRACE_ERROR("update_attribute failed with ret=0x%lx\n", ret); + free(pkey_attr); goto done; } } @@ -1410,11 +1735,11 @@ * otherwise. */ static CK_RV ab_unwrap_update_template(STDLL_TokData_t * tokdata, + SESSION * session, CK_BYTE *blob, size_t blob_len, OBJECT *obj, CK_KEY_TYPE keytype) { - ep11_target_info_t* target_info; CK_RV rc; CK_BBOOL trusted, encrypt, decrypt, wrap, unwrap, sign, sign_recover, verify, verify_recover, derive, extractable, local, @@ -1444,15 +1769,11 @@ CK_ATTRIBUTE *attr; CK_BBOOL cktrue = TRUE; - target_info = get_target_info(tokdata); - if (target_info == NULL) - return CKR_FUNCTION_FAILED; - - rc = dll_m_GetAttributeValue(blob, blob_len, attrs, - sizeof(attrs) / sizeof(CK_ATTRIBUTE), - target_info->target); - - put_target_info(tokdata, target_info); + RETRY_START(rc, tokdata) + rc = dll_m_GetAttributeValue(blob, blob_len, attrs, + sizeof(attrs) / sizeof(CK_ATTRIBUTE), + target_info->target); + RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { TRACE_ERROR("Retrieving attributes from AB unwrapped key failed, rc=0x%lx\n", @@ -1631,8 +1952,8 @@ check_types = &check_types_pub[0]; attr_cnt = sizeof(check_types_pub) / sizeof(CK_ULONG); } - /* do nothing for CKM_DH_PKCS_KEY_PAIR_GEN - and CKM_DH_PKCS_PARAMETER_GEN and CKK_IBM_PQC_DILITHIUM */ + /* do nothing for CKM_DH_PKCS_KEY_PAIR_GEN, CKK_IBM_PQC_DILITHIUM, + and CKK_IBM_PQC_KYBER */ break; case CKO_PRIVATE_KEY: if ((kt == CKK_EC) || (kt == CKK_ECDSA) || (kt == CKK_DSA)) { @@ -1647,7 +1968,7 @@ check_types = &check_types_derive[0]; attr_cnt = sizeof(check_types_derive) / sizeof(CK_ULONG); } - /* Do nothing for CKK_IBM_PQC_DILITHIUM */ + /* Do nothing for CKK_IBM_PQC_DILITHIUM and CKK_IBM_PQC_KYBER */ break; default: return CKR_OK; @@ -1741,28 +2062,11 @@ #define EP11_DEFAULT_CPFILTER_FILE "ep11cpfilter.conf" -/* error rc for reading the adapter config file */ -static const int APQN_FILE_INV = 3; -static const int APQN_FILE_INV_FILE_SIZE = 5; -static const int APQN_FILE_SYNTAX_ERROR_0 = 7; -static const int APQN_FILE_SYNTAX_ERROR_1 = 8; -static const int APQN_FILE_SYNTAX_ERROR_2 = 9; -static const int APQN_FILE_SYNTAX_ERROR_3 = 10; -static const int APQN_FILE_SYNTAX_ERROR_4 = 11; -static const int APQN_FILE_SYNTAX_ERROR_5 = 12; -static const int APQN_FILE_NO_APQN_GIVEN = 13; -static const int APQN_FILE_NO_APQN_MODE = 14; -static const int APQN_FILE_UNEXPECTED_END_OF_FILE = 15; -static const int APQN_FILE_SYNTAX_ERROR_6 = 16; -static const int APQN_FILE_SYNTAX_ERROR_7 = 17; -static const int APQN_FILE_SYNTAX_ERROR_8 = 18; -static const int APQN_OUT_OF_MEMORY = 19; - -static int read_adapter_config_file(STDLL_TokData_t * tokdata, - const char *conf_name); -static int read_cp_filter_config_file(STDLL_TokData_t *tokdata, - const char *conf_name, - cp_config_t ** cp_config); +static CK_RV read_adapter_config_file(STDLL_TokData_t * tokdata, + const char *conf_name); +static CK_RV read_cp_filter_config_file(STDLL_TokData_t *tokdata, + const char *conf_name, + cp_config_t ** cp_config); static CK_RV ep11_error_to_pkcs11_error(CK_RV rc, SESSION *session) { @@ -1805,7 +2109,8 @@ */ static CK_BBOOL attr_applicable_for_ep11(STDLL_TokData_t * tokdata, CK_ATTRIBUTE *attr, CK_KEY_TYPE ktype, - CK_OBJECT_CLASS class, int curve_type) + CK_OBJECT_CLASS class, int curve_type, + CK_MECHANISM_PTR mech) { ep11_private_data_t *ep11_data = tokdata->private_data; @@ -1823,9 +2128,12 @@ case CKK_RSA: if (class == CKO_PRIVATE_KEY && attr->type == CKA_PUBLIC_EXPONENT) return CK_FALSE; + if (attr->type == CKA_DERIVE) + return CK_FALSE; break; case CKK_EC: - if (class == CKO_PRIVATE_KEY && attr->type == CKA_EC_PARAMS) + if (class == CKO_PRIVATE_KEY && attr->type == CKA_EC_PARAMS && + mech->mechanism != CKM_IBM_BTC_DERIVE) return CK_FALSE; if (attr->type == CKA_ENCRYPT || attr->type == CKA_DECRYPT || attr->type == CKA_WRAP || attr->type == CKA_UNWRAP) @@ -1835,13 +2143,15 @@ return CK_FALSE; if (class == CKO_PUBLIC_KEY && curve_type == MONTGOMERY_CURVE && attr->type == CKA_VERIFY) return CK_FALSE; - /* Edwards curves cannot be used for derive */ - if (curve_type == EDWARDS_CURVE && attr->type == CKA_DERIVE) + /* Edwards curves cannot be used for derive (except for CKM_IBM_BTC_DERIVE) */ + if (curve_type == EDWARDS_CURVE && attr->type == CKA_DERIVE && + mech->mechanism != CKM_IBM_BTC_DERIVE) return CK_FALSE; break; case CKK_DSA: if (attr->type == CKA_ENCRYPT || attr->type == CKA_DECRYPT || - attr->type == CKA_WRAP || attr->type == CKA_UNWRAP) + attr->type == CKA_WRAP || attr->type == CKA_UNWRAP || + attr->type == CKA_DERIVE) return CK_FALSE; if (attr->type == CKA_PRIME || attr->type == CKA_SUBPRIME || attr->type == CKA_BASE) @@ -1857,7 +2167,17 @@ break; case CKK_IBM_PQC_DILITHIUM: if (attr->type == CKA_ENCRYPT || attr->type == CKA_DECRYPT || - attr->type == CKA_WRAP || attr->type == CKA_UNWRAP) + attr->type == CKA_WRAP || attr->type == CKA_UNWRAP || + attr->type == CKA_DERIVE || + attr->type == CKA_IBM_DILITHIUM_KEYFORM || + attr->type == CKA_IBM_DILITHIUM_MODE) + return CK_FALSE; + break; + case CKK_IBM_PQC_KYBER: + if (attr->type == CKA_SIGN || attr->type == CKA_VERIFY || + attr->type == CKA_WRAP || attr->type == CKA_UNWRAP || + attr->type == CKA_IBM_KYBER_KEYFORM || + attr->type == CKA_IBM_KYBER_MODE) return CK_FALSE; break; default: @@ -1874,11 +2194,12 @@ static CK_RV build_ep11_attrs(STDLL_TokData_t * tokdata, TEMPLATE *template, CK_ATTRIBUTE_PTR *p_attrs, CK_ULONG_PTR p_attrs_len, CK_KEY_TYPE ktype, CK_OBJECT_CLASS class, - int curve_type) + int curve_type, CK_MECHANISM_PTR mech) { DL_NODE *node; CK_ATTRIBUTE_PTR attr; CK_RV rc; + CK_ULONG value_len = 0; node = template->attribute_list; while (node != NULL) { @@ -1889,13 +2210,32 @@ case CKA_NEVER_EXTRACTABLE: case CKA_LOCAL: break; + /* EP11 does not like empty (zero length) attributes of that types */ + case CKA_PUBLIC_KEY_INFO: + if (attr->ulValueLen == 0) + break; + /* Fallthrough */ default: if (attr->ulValueLen > 0 && attr->pValue == NULL) return CKR_ATTRIBUTE_VALUE_INVALID; - if (attr_applicable_for_ep11(tokdata, attr, ktype, class, curve_type)) { - rc = add_to_attribute_array(p_attrs, p_attrs_len, attr->type, - attr->pValue, attr->ulValueLen); + if (attr_applicable_for_ep11(tokdata, attr, ktype, class, + curve_type, mech)) { + if (attr->type == CKA_VALUE_LEN && ktype == CKK_AES_XTS) { + value_len = *(CK_ULONG *)attr->pValue / 2; + rc = add_to_attribute_array(p_attrs, p_attrs_len, attr->type, + (CK_BYTE *)&value_len, + sizeof(value_len)); + } else if (attr->type == CKA_KEY_TYPE && + *(CK_KEY_TYPE *)attr->pValue == CKK_AES_XTS && + ktype == CKK_AES) { + rc = add_to_attribute_array(p_attrs, p_attrs_len, CKA_KEY_TYPE, + (CK_BYTE *)&ktype, sizeof(ktype)); + } else { + rc = add_to_attribute_array(p_attrs, p_attrs_len, attr->type, + attr->pValue, attr->ulValueLen); + } + if (rc != CKR_OK) { TRACE_ERROR("Adding attribute failed type=0x%lx rc=0x%lx\n", attr->type, rc); @@ -1937,7 +2277,8 @@ ep11_session_t *ep11_session = (ep11_session_t *) sess->private_data; /* tell ep11 the attributes the user specified */ - rc = build_ep11_attrs(tokdata, key_obj->template, &p_attrs, &attrs_len, ktype, CKO_SECRET_KEY, -1); + rc = build_ep11_attrs(tokdata, key_obj->template, &p_attrs, &attrs_len, + ktype, CKO_SECRET_KEY, -1, &mech); if (rc != CKR_OK) goto rawkey_2_blob_end; @@ -1968,7 +2309,7 @@ if (rc != CKR_OK) { TRACE_ERROR("%s RSA/EC check private key attributes failed with " "rc=0x%lx\n", __func__, rc); - return rc; + goto rawkey_2_blob_end; } trace_attributes(__func__, "Import sym.:", new_p_attrs, new_attrs_len); @@ -1990,6 +2331,7 @@ if (rc != CKR_OK) { rc = ep11_error_to_pkcs11_error(rc, sess); TRACE_ERROR("%s unwrap blen=%zd rc=0x%lx\n", __func__, *blen, rc); + goto rawkey_2_blob_end; } else { TRACE_INFO("%s unwrap blen=%zd rc=0x%lx\n", __func__, *blen, rc); @@ -2086,6 +2428,12 @@ __func__, ep11_data->raw2key_wrap_blob_l, rc); } + if (check_expected_mkvp(tokdata, ep11_data->raw2key_wrap_blob, + ep11_data->raw2key_wrap_blob_l) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + } + put_target_info(tokdata, target_info); return rc; } @@ -2096,7 +2444,7 @@ #define DLOPEN_FLAGS RTLD_NOW #endif -static void *ep11_load_host_lib() +static void *ep11_load_host_lib(void) { void *lib_ep11; char *ep11_lib_name; @@ -2118,11 +2466,19 @@ return lib_ep11; } - ep11_lib_name = EP11SHAREDLIB_V3; + ep11_lib_name = EP11SHAREDLIB_V4; lib_ep11 = dlopen(ep11_lib_name, DLOPEN_FLAGS); if (lib_ep11 == NULL) { TRACE_DEVEL("%s Error loading shared library '%s', trying '%s'\n", + __func__, EP11SHAREDLIB_V4, EP11SHAREDLIB_V3); + /* Try version 3 instead */ + ep11_lib_name = EP11SHAREDLIB_V3; + lib_ep11 = dlopen(ep11_lib_name, DLOPEN_FLAGS); + } + + if (lib_ep11 == NULL) { + TRACE_DEVEL("%s Error loading shared library '%s', trying '%s'\n", __func__, EP11SHAREDLIB_V3, EP11SHAREDLIB_V2); /* Try version 2 instead */ ep11_lib_name = EP11SHAREDLIB_V2; @@ -2148,9 +2504,9 @@ if (lib_ep11 == NULL) { errstr = dlerror(); OCK_SYSLOG(LOG_ERR, - "%s: Error loading shared library '%s[.3|.2|.1]' [%s]\n", + "%s: Error loading shared library '%s[.4][.3|.2|.1]' [%s]\n", __func__, EP11SHAREDLIB, errstr); - TRACE_ERROR("%s Error loading shared library '%s[.3|.2|.1]' [%s]\n", + TRACE_ERROR("%s Error loading shared library '%s[.4][.3|.2|.1]' [%s]\n", __func__, EP11SHAREDLIB, errstr); return NULL; } @@ -2277,21 +2633,28 @@ return default_libica ? CKR_OK : CKR_FUNCTION_FAILED; } - *(void **)(&libica->ica_sha1) = dlsym(libica->library, "ica_sha1"); - *(void **)(&libica->ica_sha224) = dlsym(libica->library, "ica_sha224"); - *(void **)(&libica->ica_sha256) = dlsym(libica->library, "ica_sha256"); - *(void **)(&libica->ica_sha384) = dlsym(libica->library, "ica_sha384"); - *(void **)(&libica->ica_sha512) = dlsym(libica->library, "ica_sha512"); - *(void **)(&libica->ica_sha512_224) = - dlsym(libica->library, "ica_sha512_224"); - *(void **)(&libica->ica_sha512_256) = - dlsym(libica->library, "ica_sha512_256"); + *(void **)(&libica->ica_fips_status) = dlsym(libica->library, "ica_fips_status"); + if (libica->ica_fips_status != NULL && + libica->ica_fips_status() > ICA_FIPS_MODE) { + TRACE_WARNING("%s: libica FIPS selftests failed, disable use of libica\n", + __func__); + } else { + *(void **)(&libica->ica_sha1) = dlsym(libica->library, "ica_sha1"); + *(void **)(&libica->ica_sha224) = dlsym(libica->library, "ica_sha224"); + *(void **)(&libica->ica_sha256) = dlsym(libica->library, "ica_sha256"); + *(void **)(&libica->ica_sha384) = dlsym(libica->library, "ica_sha384"); + *(void **)(&libica->ica_sha512) = dlsym(libica->library, "ica_sha512"); + *(void **)(&libica->ica_sha512_224) = + dlsym(libica->library, "ica_sha512_224"); + *(void **)(&libica->ica_sha512_256) = + dlsym(libica->library, "ica_sha512_256"); #ifdef SHA3_224 - *(void **)(&libica->ica_sha3_224) = dlsym(libica->library, "ica_sha3_224"); - *(void **)(&libica->ica_sha3_256) = dlsym(libica->library, "ica_sha3_256"); - *(void **)(&libica->ica_sha3_384) = dlsym(libica->library, "ica_sha3_384"); - *(void **)(&libica->ica_sha3_512) = dlsym(libica->library, "ica_sha3_512"); + *(void **)(&libica->ica_sha3_224) = dlsym(libica->library, "ica_sha3_224"); + *(void **)(&libica->ica_sha3_256) = dlsym(libica->library, "ica_sha3_256"); + *(void **)(&libica->ica_sha3_384) = dlsym(libica->library, "ica_sha3_384"); + *(void **)(&libica->ica_sha3_512) = dlsym(libica->library, "ica_sha3_512"); #endif + } *(void **)(&libica->ica_cleanup) = dlsym(libica->library, "ica_cleanup"); /* No error checking, each of the libica functions is allowed to be NULL */ @@ -2335,6 +2698,7 @@ OCK_SYSLOG(LOG_ERR, "%s: Failed to initialize the target lock\n", __func__); rc = CKR_CANT_LOCK; + free(ep11_data); goto error; } @@ -2345,7 +2709,6 @@ rc = read_adapter_config_file(tokdata, conf_name); if (rc != CKR_OK) { TRACE_ERROR("%s ep11 config file error rc=0x%lx\n", __func__, rc); - rc = CKR_GENERAL_ERROR; goto error; } @@ -2523,7 +2886,7 @@ attr = node->data; if (!attr_applicable_for_ep11(tokdata, attr, keytype, - CKO_PUBLIC_KEY, curve_type)) + CKO_PUBLIC_KEY, curve_type, &mech)) goto make_maced_spki_next; switch (attr->type) { @@ -2643,14 +3006,179 @@ return curve_type; } +/* import a AES-XTS key, that is, make a blob for a AES XTS key + * that was not created by EP11 hardware, encrypt the key by the wrap key, + * unwrap it by the wrap key + */ +static CK_RV import_aes_xts_key(STDLL_TokData_t *tokdata, SESSION *sess, + OBJECT *aes_xts_key_obj, + CK_BYTE *blob, size_t *blob_size) +{ + ep11_private_data_t *ep11_data = tokdata->private_data; + CK_BYTE cipher[MAX_BLOBSIZE]; + CK_ULONG clen = sizeof(cipher); + CK_BYTE csum[MAX_CSUMSIZE]; + size_t cslen = sizeof(csum); + CK_BYTE iv[AES_BLOCK_SIZE]; + size_t blob_size2 = *blob_size; + CK_MECHANISM mech = { CKM_AES_CBC_PAD, iv, AES_BLOCK_SIZE }; + CK_RV rc; + CK_ATTRIBUTE_PTR p_attrs = NULL; + CK_ULONG attrs_len = 0; + CK_ATTRIBUTE_PTR new_p_attrs = NULL; + CK_ULONG new_attrs_len = 0; + CK_ATTRIBUTE *attr = NULL; + unsigned char *ep11_pin_blob = NULL; + CK_ULONG ep11_pin_blob_len = 0; + ep11_session_t *ep11_session = (ep11_session_t*) sess->private_data; + + rc = template_attribute_get_non_empty(aes_xts_key_obj->template, CKA_VALUE, + &attr); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find CKA_VALUE for the key.\n"); + return rc; + } + + /* tell ep11 the attributes the user specified */ + rc = build_ep11_attrs(tokdata, aes_xts_key_obj->template, &p_attrs, + &attrs_len, CKK_AES, CKO_SECRET_KEY, -1, &mech); + if (rc != CKR_OK) + goto import_aes_xts_key_end; + + rc = ep11tok_pkey_check_aes_xts(tokdata, aes_xts_key_obj, CKM_AES_XTS); + if (rc != CKR_OK) { + TRACE_ERROR("%s EP11 AES XTS is not supported: rc=0x%lx\n", __func__, rc); + goto import_aes_xts_key_end; + } + + memset(cipher, 0, sizeof(cipher)); + memcpy(iv, "1234567812345678", AES_BLOCK_SIZE); + + /* + * calls the ep11 lib (which in turns sends the request to the card), + * all m_ function are ep11 functions + */ + RETRY_START(rc, tokdata) + rc = dll_m_EncryptSingle(ep11_data->raw2key_wrap_blob, + ep11_data->raw2key_wrap_blob_l, &mech, + attr->pValue, attr->ulValueLen / 2, + cipher, &clen, target_info->target); + RETRY_END(rc, tokdata, sess) + + if (rc != CKR_OK) { + rc = ep11_error_to_pkcs11_error(rc, sess); + TRACE_ERROR("%s encrypt ksize=0x%lx clen=0x%lx rc=0x%lx\n", __func__, + attr->ulValueLen / 2, clen, rc); + goto import_aes_xts_key_end; + } else { + TRACE_INFO("%s encrypt ksize=0x%lx clen=0x%lx rc=0x%lx\n", __func__, + attr->ulValueLen / 2, clen, rc); + } + + rc = check_key_attributes(tokdata, CKK_AES, CKO_SECRET_KEY, p_attrs, + attrs_len, &new_p_attrs, &new_attrs_len, -1); + if (rc != CKR_OK) { + TRACE_ERROR("%s AES XTS check private key attributes failed with " + "rc=0x%lx\n", __func__, rc); + goto import_aes_xts_key_end; + } + + trace_attributes(__func__, "Import sym.:", new_p_attrs, new_attrs_len); + + ep11_get_pin_blob(ep11_session, object_is_session_object(aes_xts_key_obj), + &ep11_pin_blob, &ep11_pin_blob_len); + + /* the encrypted key is decrypted and a blob is built, + * card accepts only blobs as keys + */ + RETRY_START(rc, tokdata) + rc = dll_m_UnwrapKey(cipher, clen, ep11_data->raw2key_wrap_blob, + ep11_data->raw2key_wrap_blob_l, NULL, ~0, ep11_pin_blob, + ep11_pin_blob_len, &mech, new_p_attrs, new_attrs_len, + blob, blob_size, csum, &cslen, target_info->target); + RETRY_END(rc, tokdata, sess) + + if (rc != CKR_OK) { + rc = ep11_error_to_pkcs11_error(rc, sess); + TRACE_ERROR("%s unwrap blen=%zd rc=0x%lx\n", __func__, *blob_size, rc); + goto import_aes_xts_key_end; + } else { + TRACE_INFO("%s unwrap blen=%zd rc=0x%lx\n", __func__, *blob_size, rc); + } + + memset(cipher, 0, sizeof(cipher)); + + /* + * calls the ep11 lib (which in turns sends the request to the card), + * all m_ function are ep11 functions + */ + RETRY_START(rc, tokdata) + rc = dll_m_EncryptSingle(ep11_data->raw2key_wrap_blob, + ep11_data->raw2key_wrap_blob_l, &mech, + ((CK_BYTE *)attr->pValue) + attr->ulValueLen / 2, + attr->ulValueLen / 2, cipher, &clen, + target_info->target); + RETRY_END(rc, tokdata, sess) + + if (rc != CKR_OK) { + rc = ep11_error_to_pkcs11_error(rc, sess); + TRACE_ERROR("%s encrypt ksize=0x%lx clen=0x%lx rc=0x%lx\n", + __func__, attr->ulValueLen / 2, clen, rc); + goto import_aes_xts_key_end; + } else { + TRACE_INFO("%s encrypt ksize=0x%lx clen=0x%lx rc=0x%lx\n", __func__, + attr->ulValueLen / 2, clen, rc); + } + + trace_attributes(__func__, "Import sym.:", new_p_attrs, new_attrs_len); + + /* update the remaining buffer size in blob */ + blob_size2 = blob_size2 - *blob_size; + + /* the encrypted key is decrypted and a blob is built, + * card accepts only blobs as keys + */ + RETRY_START(rc, tokdata) + rc = dll_m_UnwrapKey(cipher, clen, + ep11_data->raw2key_wrap_blob, + ep11_data->raw2key_wrap_blob_l, NULL, ~0, + ep11_pin_blob, ep11_pin_blob_len, &mech, + new_p_attrs, new_attrs_len, blob + *blob_size, + &blob_size2, csum, &cslen, target_info->target); + RETRY_END(rc, tokdata, sess) + + if (rc != CKR_OK) { + rc = ep11_error_to_pkcs11_error(rc, sess); + TRACE_ERROR("%s unwrap blen=%zd rc=0x%lx\n", __func__, blob_size2, rc); + goto import_aes_xts_key_end; + } else { + TRACE_INFO("%s unwrap blen=%zd rc=0x%lx\n", __func__, blob_size2, rc); + } + + /* update the concatenated blobsize */ + *blob_size = *blob_size + blob_size2; + + cleanse_attribute(aes_xts_key_obj->template, CKA_VALUE); + +import_aes_xts_key_end: + if (rc != CKR_OK) + cleanse_attribute(aes_xts_key_obj->template, CKA_VALUE); + if (p_attrs != NULL) + cleanse_and_free_attribute_array(p_attrs, attrs_len); + if (new_p_attrs) + cleanse_and_free_attribute_array(new_p_attrs, new_attrs_len); + return rc; +} + /* * makes blobs for private imported RSA keys and * SPKIs for public imported RSA keys. * Similar to rawkey_2_blob, but keys must follow a standard BER encoding. */ -static CK_RV import_RSA_key(STDLL_TokData_t * tokdata, SESSION * sess, - OBJECT * rsa_key_obj, - CK_BYTE * blob, size_t * blob_size) +static CK_RV import_RSA_key(STDLL_TokData_t *tokdata, SESSION *sess, + OBJECT *rsa_key_obj, + CK_BYTE *blob, size_t *blob_size, + CK_BYTE *spki, size_t *spki_size) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_RV rc; @@ -2662,8 +3190,6 @@ CK_ULONG attrs_len = 0; CK_ATTRIBUTE_PTR new_p_attrs = NULL; CK_ULONG new_attrs_len = 0; - CK_BYTE csum[MAX_BLOBSIZE]; - CK_ULONG cslen = sizeof(csum); CK_OBJECT_CLASS class; CK_BYTE *data = NULL; CK_ULONG data_len; @@ -2684,7 +3210,8 @@ /* m_Unwrap builds key blob in the card, * tell ep11 the attributes the user specified for that key. */ - rc = build_ep11_attrs(tokdata, rsa_key_obj->template, &p_attrs, &attrs_len, CKK_RSA, class, -1); + rc = build_ep11_attrs(tokdata, rsa_key_obj->template, &p_attrs, &attrs_len, + CKK_RSA, class, -1, &mech_w); if (rc != CKR_OK) goto import_RSA_key_end; @@ -2733,6 +3260,8 @@ goto import_RSA_key_end; } + *spki_size = 0; /* common code will extract SPKI from object */ + } else { /* imported private RSA key goes here */ @@ -2786,7 +3315,7 @@ ep11_data->raw2key_wrap_blob_l, NULL, ~0, ep11_pin_blob, ep11_pin_blob_len, &mech_w, new_p_attrs, new_attrs_len, blob, blob_size, - csum, &cslen, target_info->target); + spki, spki_size, target_info->target); RETRY_END(rc, tokdata, sess) if (rc != CKR_OK) { @@ -2823,9 +3352,10 @@ * SPKIs for public imported EC keys. * Similar to rawkey_2_blob, but keys must follow a standard BER encoding. */ -static CK_RV import_EC_key(STDLL_TokData_t * tokdata, SESSION * sess, - OBJECT * ec_key_obj, - CK_BYTE * blob, size_t * blob_size) +static CK_RV import_EC_key(STDLL_TokData_t *tokdata, SESSION *sess, + OBJECT *ec_key_obj, + CK_BYTE *blob, size_t *blob_size, + CK_BYTE *spki, size_t *spki_size) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_RV rc; @@ -2837,8 +3367,6 @@ CK_ULONG attrs_len = 0; CK_ATTRIBUTE_PTR new_p_attrs = NULL; CK_ULONG new_attrs_len = 0; - CK_BYTE csum[MAX_BLOBSIZE]; - CK_ULONG cslen = sizeof(csum); CK_OBJECT_CLASS class; CK_BYTE *data = NULL; CK_ULONG data_len; @@ -2867,7 +3395,7 @@ * tell ep11 the attributes the user specified for that key. */ rc = build_ep11_attrs(tokdata, ec_key_obj->template, &p_attrs, &attrs_len, - CKK_EC, class, (int)curve->curve_type); + CKK_EC, class, (int)curve->curve_type, &mech_w); if (rc != CKR_OK) goto import_EC_key_end; @@ -2961,6 +3489,8 @@ goto import_EC_key_end; } + *spki_size = 0; /* common code will extract SPKI from object */ + } else { /* imported private EC key goes here */ @@ -3017,7 +3547,8 @@ ep11_pin_blob, ep11_pin_blob_len, &mech_w, new_p_attrs, new_attrs_len, blob, - blob_size, csum, &cslen, target_info->target); + blob_size, spki, spki_size, + target_info->target); RETRY_END(rc, tokdata, sess) if (rc != CKR_OK) { @@ -3051,9 +3582,10 @@ * SPKIs for public imported DSA keys. * Similar to rawkey_2_blob, but keys must follow a standard BER encoding. */ -static CK_RV import_DSA_key(STDLL_TokData_t * tokdata, SESSION * sess, - OBJECT * dsa_key_obj, - CK_BYTE * blob, size_t * blob_size) +static CK_RV import_DSA_key(STDLL_TokData_t *tokdata, SESSION *sess, + OBJECT *dsa_key_obj, + CK_BYTE *blob, size_t *blob_size, + CK_BYTE *spki, size_t *spki_size) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_RV rc; @@ -3065,8 +3597,6 @@ CK_ULONG attrs_len = 0; CK_ATTRIBUTE_PTR new_p_attrs = NULL; CK_ULONG new_attrs_len = 0; - CK_BYTE csum[MAX_BLOBSIZE]; - CK_ULONG cslen = sizeof(csum); CK_OBJECT_CLASS class; CK_BYTE *data = NULL; CK_ULONG data_len; @@ -3086,7 +3616,8 @@ /* m_Unwrap builds key blob in the card, * tell ep11 the attributes the user specified for that key. */ - rc = build_ep11_attrs(tokdata, dsa_key_obj->template, &p_attrs, &attrs_len, CKK_DSA, class, -1); + rc = build_ep11_attrs(tokdata, dsa_key_obj->template, &p_attrs, &attrs_len, + CKK_DSA, class, -1, &mech_w); if (rc != CKR_OK) goto import_DSA_key_end; @@ -3152,6 +3683,8 @@ goto import_DSA_key_end; } + *spki_size = 0; /* common code will extract SPKI from object */ + } else { /* imported private DSA key goes here */ @@ -3208,7 +3741,8 @@ ep11_pin_blob, ep11_pin_blob_len, &mech_w, new_p_attrs, new_attrs_len, blob, - blob_size, csum, &cslen, target_info->target); + blob_size, spki, spki_size, + target_info->target); RETRY_END(rc, tokdata, sess) if (rc != CKR_OK) { @@ -3240,9 +3774,10 @@ * SPKIs for public imported DH keys. * Similar to rawkey_2_blob, but keys must follow a standard BER encoding. */ -static CK_RV import_DH_key(STDLL_TokData_t * tokdata, SESSION * sess, - OBJECT * dh_key_obj, - CK_BYTE * blob, size_t * blob_size) +static CK_RV import_DH_key(STDLL_TokData_t *tokdata, SESSION *sess, + OBJECT *dh_key_obj, + CK_BYTE *blob, size_t *blob_size, + CK_BYTE *spki, size_t *spki_size) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_RV rc; @@ -3254,8 +3789,6 @@ CK_ULONG attrs_len = 0; CK_ATTRIBUTE_PTR new_p_attrs = NULL; CK_ULONG new_attrs_len = 0; - CK_BYTE csum[MAX_BLOBSIZE]; - CK_ULONG cslen = sizeof(csum); CK_OBJECT_CLASS class; CK_BYTE *data = NULL; CK_ULONG data_len; @@ -3275,7 +3808,8 @@ /* m_Unwrap builds key blob in the card, * tell ep11 the attributes the user specified for that key. */ - rc = build_ep11_attrs(tokdata, dh_key_obj->template, &p_attrs, &attrs_len, CKK_DH, class, -1); + rc = build_ep11_attrs(tokdata, dh_key_obj->template, &p_attrs, &attrs_len, + CKK_DH, class, -1, &mech_w); if (rc != CKR_OK) goto import_DH_key_end; @@ -3333,6 +3867,8 @@ goto import_DH_key_end; } + *spki_size = 0; /* common code will extract SPKI from object */ + } else { CK_ATTRIBUTE *value; CK_ATTRIBUTE *value_bits; @@ -3400,7 +3936,8 @@ ep11_pin_blob, ep11_pin_blob_len, &mech_w, new_p_attrs, new_attrs_len, blob, - blob_size, csum, &cslen, target_info->target); + blob_size, spki, spki_size, + target_info->target); RETRY_END(rc, tokdata, sess) if (rc != CKR_OK) { @@ -3443,13 +3980,14 @@ } /* - * makes blobs for private imported IBM Dilithium keys and - * SPKIs for public imported IBM Dilithium keys. + * makes blobs for private imported IBM PQC keys and + * SPKIs for public imported IBM PQC keys. * Similar to rawkey_2_blob, but keys must follow a standard BER encoding. */ -static CK_RV import_IBM_Dilithium_key(STDLL_TokData_t * tokdata, SESSION * sess, - OBJECT * dilithium_key_obj, - CK_BYTE * blob, size_t * blob_size) +static CK_RV import_IBM_pqc_key(STDLL_TokData_t *tokdata, SESSION *sess, + OBJECT *pqc_key_obj, CK_KEY_TYPE keytype, + CK_BYTE *blob, size_t *blob_size, + CK_BYTE *spki, size_t *spki_size) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_RV rc; @@ -3461,20 +3999,36 @@ CK_ULONG attrs_len = 0; CK_ATTRIBUTE_PTR new_p_attrs = NULL; CK_ULONG new_attrs_len = 0; - CK_BYTE csum[MAX_BLOBSIZE]; - CK_ULONG cslen = sizeof(csum); CK_OBJECT_CLASS class; CK_BYTE *data = NULL; CK_ULONG data_len; unsigned char *ep11_pin_blob = NULL; CK_ULONG ep11_pin_blob_len = 0; ep11_session_t *ep11_session = (ep11_session_t *) sess->private_data; - CK_BYTE *pubkey = NULL; + CK_ATTRIBUTE *value_attr = NULL; + CK_BBOOL data_alloced = TRUE; + const struct pqc_oid *oid; + const char *key_type_str; + CK_MECHANISM_TYPE pqc_mech; + + switch (keytype) { + case CKK_IBM_PQC_DILITHIUM: + key_type_str = "Dilithium"; + pqc_mech = CKM_IBM_DILITHIUM; + break; + case CKK_IBM_PQC_KYBER: + key_type_str = "Kyber"; + pqc_mech = CKM_IBM_KYBER; + break; + default: + TRACE_ERROR("Invalid key type provided for %s\n ", __func__); + return CKR_KEY_TYPE_INCONSISTENT; + } memcpy(iv, "1234567812345678", AES_BLOCK_SIZE); /* need class for secret/public key info */ - rc = template_attribute_get_ulong(dilithium_key_obj->template, CKA_CLASS, + rc = template_attribute_get_ulong(pqc_key_obj->template, CKA_CLASS, &class); if (rc != CKR_OK) { TRACE_ERROR("Could not find CKA_CLASS for the key.\n"); @@ -3484,65 +4038,85 @@ /* m_Unwrap builds key blob in the card, * tell ep11 the attributes the user specified for that key. */ - rc = build_ep11_attrs(tokdata, dilithium_key_obj->template, &p_attrs, &attrs_len, CKK_IBM_PQC_DILITHIUM, class, -1); + rc = build_ep11_attrs(tokdata, pqc_key_obj->template, + &p_attrs, &attrs_len, + keytype, class, -1, &mech_w); if (rc != CKR_OK) goto done; if (class != CKO_PRIVATE_KEY) { + /* Make an SPKI for the public IBM PQC key */ - /* Make an SPKI for the public IBM Dilithium key */ - CK_ULONG keyform; - CK_ATTRIBUTE *rho; - CK_ATTRIBUTE *t1; - - /* A public IBM Dilithium key must have a keyform value */ - rc = template_attribute_get_ulong(dilithium_key_obj->template, - CKA_IBM_DILITHIUM_KEYFORM, - &keyform); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_IBM_DILITHIUM_KEYFORM for the " - "key.\n"); - goto done; - } - - /* Check if it's an expected keyform */ - if (keyform != IBM_DILITHIUM_KEYFORM_ROUND2) { - TRACE_ERROR("Keyform is not supported\n"); - rc = CKR_TEMPLATE_INCONSISTENT; - goto done; - } + /* A public IBM PQC key must either have a CKA_VALUE containing + * the SPKI, or must have a keyform/mode value and the individual + * attributes + */ + if (template_attribute_find(pqc_key_obj->template, + CKA_VALUE, &value_attr) && + value_attr->ulValueLen > 0 && value_attr ->pValue != NULL) { + /* CKA_VALUE with SPKI */ + data = value_attr ->pValue; + data_len = value_attr->ulValueLen; + data_alloced = FALSE; - /* A public IBM Dilithium key must have a rho value */ - rc = template_attribute_get_non_empty(dilithium_key_obj->template, - CKA_IBM_DILITHIUM_RHO, &rho); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_IBM_DILITHIUM_RHO for the key.\n"); - goto done; - } + /* + * Decode SPKI and add public key attributes. This also adds the + * keyform and mode attributes to the template. + */ + rc = ibm_pqc_priv_unwrap_get_data(pqc_key_obj->template, keytype, + data, data_len, FALSE); + if (rc != CKR_OK) { + TRACE_ERROR("Failed to decode SPKI from CKA_VALUE.\n"); + goto done; + } + } else { + /* Individual attributes */ + rc = ibm_pqc_publ_get_spki(pqc_key_obj->template, keytype, + FALSE, &data, &data_len); + if (rc != CKR_OK) { + TRACE_ERROR("%s public key import class=0x%lx rc=0x%lx " + "data_len=0x%lx\n", __func__, class, rc, data_len); + goto done; + } else { + TRACE_INFO("%s public key import class=0x%lx rc=0x%lx " + "data_len=0x%lx\n", __func__, class, rc, data_len); + } - /* A public IBM Dilithium key must have a t1 value */ - rc = template_attribute_get_non_empty(dilithium_key_obj->template, - CKA_IBM_DILITHIUM_T1, &t1); - if (rc != CKR_OK) { - TRACE_ERROR("Could not find CKA_IBM_DILITHIUM_T1 for the key.\n"); - goto done; - } + /* Ensure both, keyform and mode attributes are added */ + oid = ibm_pqc_get_keyform_mode(pqc_key_obj->template, pqc_mech); + if (oid == NULL) { + rc = CKR_TEMPLATE_INCOMPLETE; + goto done; + } - /* Encode the public key */ - rc = ber_encode_IBM_DilithiumPublicKey(0, &data, &data_len, rho, t1); - if (rc != CKR_OK) { - TRACE_ERROR("%s public key import class=0x%lx rc=0x%lx " - "data_len=0x%lx\n", __func__, class, rc, data_len); - goto done; - } else { - TRACE_INFO("%s public key import class=0x%lx rc=0x%lx " - "data_len=0x%lx\n", __func__, class, rc, data_len); + rc = ibm_pqc_add_keyform_mode(pqc_key_obj->template, oid, pqc_mech); + if (rc != CKR_OK) { + TRACE_ERROR("ibm_pqc_add_keyform_mode failed\n"); + goto done; + } + + /* Add SPKI as CKA_VALUE to public key (z/OS ICSF compatibility) */ + rc = build_attribute(CKA_VALUE, data, data_len, &value_attr); + if (rc != CKR_OK) { + TRACE_DEVEL("build_attribute failed\n"); + goto done; + } + + rc = template_update_attribute(pqc_key_obj->template, + value_attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(value_attr); + goto done; + } + value_attr = NULL; } /* save the SPKI as blob although it is not a blob. * The card expects MACed-SPKIs as public keys. */ - rc = make_maced_spki(tokdata, sess, dilithium_key_obj, data, data_len, + rc = make_maced_spki(tokdata, sess, pqc_key_obj, data, data_len, blob, blob_size, -1); if (rc != CKR_OK) { TRACE_ERROR("%s failed to make a MACed-SPKI rc=0x%lx\n", @@ -3550,26 +4124,69 @@ goto done; } + *spki_size = 0; /* common code will extract SPKI from object */ + } else { - /* imported private IBM Dilithium key goes here */ + /* imported private IBM PQC key goes here */ - /* extract the secret data to be wrapped - * since this is AES_CBC_PAD, padding is done in mechanism. + /* A public IBM PQC key must either have a CKA_VALUE containing + * the PKCS#8 encoded private key, or must have a keyform/mode value + * and the individual attributes */ - rc = ibm_dilithium_priv_wrap_get_data(dilithium_key_obj->template, FALSE, - &data, &data_len); - if (rc != CKR_OK) { - TRACE_DEVEL("%s Dilithium wrap get data failed\n", __func__); - goto done; + if (template_attribute_find(pqc_key_obj->template, + CKA_VALUE, &value_attr) && + value_attr->ulValueLen > 0 && value_attr ->pValue != NULL) { + /* CKA_VALUE with SPKI */ + data = value_attr ->pValue; + data_len = value_attr->ulValueLen; + data_alloced = FALSE; + + /* Decode PKCS#8 private key and add key attributes */ + rc = ibm_pqc_priv_unwrap(pqc_key_obj->template, keytype, + data, data_len, FALSE); + if (rc != CKR_OK) { + TRACE_ERROR("Failed to decode private key from CKA_VALUE.\n"); + goto done; + } + } else { + /* Extract the secret data to be wrapped since this is AES_CBC_PAD, + * padding is done in mechanism. This also adds the keyform and mode + * attributes to the template. + */ + rc = ibm_pqc_priv_wrap_get_data(pqc_key_obj->template, keytype, + FALSE, &data, &data_len); + if (rc != CKR_OK) { + TRACE_DEVEL("%s %s wrap get data failed\n", __func__, + key_type_str); + goto done; + } + + /* Ensure both, keyform and mode attributes are added */ + oid = ibm_pqc_get_keyform_mode(pqc_key_obj->template, pqc_mech); + if (oid == NULL) { + rc = CKR_TEMPLATE_INCOMPLETE; + goto done; + } + + rc = ibm_pqc_add_keyform_mode(pqc_key_obj->template, oid, pqc_mech); + if (rc != CKR_OK) { + TRACE_ERROR("ibm_pqc_add_keyform_mode failed\n"); + goto done; + } } /* encrypt */ RETRY_START(rc, tokdata) - rc = dll_m_EncryptSingle(ep11_data->raw2key_wrap_blob, - ep11_data->raw2key_wrap_blob_l, - &mech_w, data, data_len, - cipher, &cipher_l, target_info->target); + if (ep11_pqc_obj_strength_supported(target_info, pqc_mech, + pqc_key_obj)) + rc = dll_m_EncryptSingle(ep11_data->raw2key_wrap_blob, + ep11_data->raw2key_wrap_blob_l, + &mech_w, data, data_len, + cipher, &cipher_l, + target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, sess) TRACE_INFO("%s wrapping wrap key rc=0x%lx cipher_l=0x%lx\n", @@ -3582,8 +4199,7 @@ goto done; } - rc = check_key_attributes(tokdata, CKK_IBM_PQC_DILITHIUM, - CKO_PRIVATE_KEY, + rc = check_key_attributes(tokdata, keytype, CKO_PRIVATE_KEY, p_attrs, attrs_len, &new_p_attrs, &new_attrs_len, -1); if (rc != CKR_OK) { @@ -3592,12 +4208,12 @@ goto done; } - trace_attributes(__func__, "Dilithium import:", new_p_attrs, new_attrs_len); + trace_attributes(__func__, "PQC import:", new_p_attrs, new_attrs_len); - ep11_get_pin_blob(ep11_session, object_is_session_object(dilithium_key_obj), + ep11_get_pin_blob(ep11_session, object_is_session_object(pqc_key_obj), &ep11_pin_blob, &ep11_pin_blob_len); - /* calls the card, it decrypts the private Dilithium key, + /* calls the card, it decrypts the private PQC key, * reads its BER format and builds a blob. */ RETRY_START(rc, tokdata) @@ -3607,7 +4223,8 @@ ep11_pin_blob, ep11_pin_blob_len, &mech_w, new_p_attrs, new_attrs_len, blob, - blob_size, csum, &cslen, target_info->target); + blob_size, spki, spki_size, + target_info->target); RETRY_END(rc, tokdata, sess) if (rc != CKR_OK) { @@ -3619,14 +4236,24 @@ __func__, rc, *blob_size); } - cleanse_attribute(dilithium_key_obj->template, CKA_VALUE); + cleanse_attribute(pqc_key_obj->template, CKA_VALUE); + + switch (keytype) { + case CKK_IBM_PQC_DILITHIUM: + cleanse_attribute(pqc_key_obj->template, CKA_IBM_DILITHIUM_SEED); + cleanse_attribute(pqc_key_obj->template, CKA_IBM_DILITHIUM_TR); + cleanse_attribute(pqc_key_obj->template, CKA_IBM_DILITHIUM_S1); + cleanse_attribute(pqc_key_obj->template, CKA_IBM_DILITHIUM_S2); + cleanse_attribute(pqc_key_obj->template, CKA_IBM_DILITHIUM_T0); + break; + case CKK_IBM_PQC_KYBER: + cleanse_attribute(pqc_key_obj->template, CKA_IBM_KYBER_SK); + break; + } } done: - - if (pubkey) - free(pubkey); - if (data) { + if (data_alloced && data) { OPENSSL_cleanse(data, data_len); free(data); } @@ -3645,9 +4272,13 @@ CK_ATTRIBUTE *attr = NULL; CK_BYTE blob[MAX_BLOBSIZE]; size_t blobsize = sizeof(blob); + CK_BYTE spki[MAX_BLOBSIZE]; + size_t spkisize = sizeof(spki); CK_RV rc; CK_ULONG class; CK_BBOOL attrbound; + CK_BYTE *temp; + CK_ULONG temp_len; /* get key type */ rc = template_attribute_get_ulong(obj->template, CKA_KEY_TYPE, &keytype); @@ -3681,7 +4312,8 @@ /* only these keys can be imported */ switch (keytype) { case CKK_RSA: - rc = import_RSA_key(tokdata, sess, obj, blob, &blobsize); + rc = import_RSA_key(tokdata, sess, obj, blob, &blobsize, + spki, &spkisize); if (rc != CKR_OK) { TRACE_ERROR("%s import RSA key rc=0x%lx blobsize=0x%zx\n", __func__, rc, blobsize); @@ -3691,7 +4323,8 @@ __func__, rc, blobsize); break; case CKK_EC: - rc = import_EC_key(tokdata, sess, obj, blob, &blobsize); + rc = import_EC_key(tokdata, sess, obj, blob, &blobsize, + spki, &spkisize); if (rc != CKR_OK) { TRACE_ERROR("%s import EC key rc=0x%lx blobsize=0x%zx\n", __func__, rc, blobsize); @@ -3701,7 +4334,8 @@ __func__, rc, blobsize); break; case CKK_DSA: - rc = import_DSA_key(tokdata, sess, obj, blob, &blobsize); + rc = import_DSA_key(tokdata, sess, obj, blob, &blobsize, + spki, &spkisize); if (rc != CKR_OK) { TRACE_ERROR("%s import DSA key rc=0x%lx blobsize=0x%zx\n", __func__, rc, blobsize); @@ -3711,7 +4345,8 @@ __func__, rc, blobsize); break; case CKK_DH: - rc = import_DH_key(tokdata, sess, obj, blob, &blobsize); + rc = import_DH_key(tokdata, sess, obj, blob, &blobsize, + spki, &spkisize); if (rc != CKR_OK) { TRACE_ERROR("%s import DH key rc=0x%lx blobsize=0x%zx\n", __func__, rc, blobsize); @@ -3721,14 +4356,16 @@ __func__, rc, blobsize); break; case CKK_IBM_PQC_DILITHIUM: - rc = import_IBM_Dilithium_key(tokdata, sess, obj, blob, &blobsize); + case CKK_IBM_PQC_KYBER: + rc = import_IBM_pqc_key(tokdata, sess, obj, keytype, blob, &blobsize, + spki, &spkisize); if (rc != CKR_OK) { - TRACE_ERROR("%s import IBM Dilithium key rc=0x%lx blobsize=0x%zx\n", - __func__, rc, blobsize); + TRACE_ERROR("%s import IBM PQC key kytype=0x%lx rc=0x%lx blobsize=0x%zx\n", + __func__, keytype, rc, blobsize); return rc; } - TRACE_INFO("%s import IBM Dilithium key rc=0x%lx blobsize=0x%zx\n", - __func__, rc, blobsize); + TRACE_INFO("%s import IBM PQC key kytype=0x%lx rc=0x%lx blobsize=0x%zx\n", + __func__, keytype, rc, blobsize); break; case CKK_DES2: case CKK_DES3: @@ -3756,12 +4393,41 @@ TRACE_INFO("%s rawkey_2_blob rc=0x%lx blobsize=0x%zx\n", __func__, rc, blobsize); - + break; + case CKK_AES_XTS: + rc = import_aes_xts_key(tokdata, sess, obj, blob, &blobsize); + if (rc != CKR_OK) { + TRACE_ERROR("%s import AES XTS key rc=0x%lx blobsize=0x%zx\n", + __func__, rc, blobsize); + return rc; + } + TRACE_INFO("%s import AES XTS key rc=0x%lx blobsize=0x%zx\n", + __func__, rc, blobsize); break; default: return CKR_KEY_FUNCTION_NOT_PERMITTED; } + switch (class) { + case CKO_PRIVATE_KEY: + case CKO_SECRET_KEY: + if (check_expected_mkvp(tokdata, blob, keytype == CKK_AES_XTS ? + blobsize / 2 : blobsize) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + if (keytype == CKK_AES_XTS) { + if (check_expected_mkvp(tokdata, blob + blobsize / 2, + blobsize / 2) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + return CKR_DEVICE_ERROR; + } + } + break; + default: + break; + } + /* store the blob in the key obj */ rc = build_attribute(CKA_IBM_OPAQUE, blob, blobsize, &attr); if (rc != CKR_OK) { @@ -3777,7 +4443,33 @@ return rc; } - rc = update_ep11_attrs_from_blob(tokdata, obj->template); + if (spkisize > 0 && (class == CKO_PRIVATE_KEY || class == CKO_PUBLIC_KEY)) { + /* spki may be a MACed SPKI, get length of SPKI part only */ + rc = ber_decode_SEQUENCE(spki, &temp, &temp_len, &spkisize); + if (rc != CKR_OK) { + TRACE_ERROR("%s ber_decode_SEQUENCE failed rc=0x%lx\n", + __func__, rc); + return rc; + } + + rc = build_attribute(CKA_PUBLIC_KEY_INFO, spki, spkisize, &attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, + rc); + return rc; + } + + rc = template_update_attribute(obj->template, attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(attr); + return rc; + } + } + + rc = update_ep11_attrs_from_blob(tokdata, sess, obj->template, + (keytype == CKK_AES_XTS)); if (rc != CKR_OK) { TRACE_ERROR("%s update_ep11_attrs_from_blob failed with rc=0x%lx\n", __func__, rc); @@ -3787,13 +4479,13 @@ return CKR_OK; } - CK_RV ep11tok_generate_key(STDLL_TokData_t * tokdata, SESSION * session, CK_MECHANISM_PTR mech, CK_ATTRIBUTE_PTR attrs, CK_ULONG attrs_len, CK_OBJECT_HANDLE_PTR handle) { - CK_BYTE blob[MAX_BLOBSIZE]; + CK_BYTE blob[MAX_BLOBSIZE], blob2[MAX_BLOBSIZE]; size_t blobsize = sizeof(blob); + size_t blobsize2 = sizeof(blob2); CK_BYTE csum[MAX_CSUMSIZE]; size_t csum_len = sizeof(csum); CK_ATTRIBUTE *attr = NULL; @@ -3804,12 +4496,15 @@ CK_ATTRIBUTE_PTR new_attrs2 = NULL; CK_ULONG new_attrs_len = 0, new_attrs2_len = 0; CK_RV rc; + CK_BOOL xts = FALSE; unsigned char *ep11_pin_blob = NULL; CK_ULONG ep11_pin_blob_len = 0; ep11_session_t *ep11_session = (ep11_session_t *) session->private_data; + CK_MECHANISM mech2 = {CKM_AES_KEY_GEN, NULL, 0}; memset(blob, 0, sizeof(blob)); memset(csum, 0, sizeof(csum)); + memset(blob2, 0, sizeof(blob2)); /* Get the keytype to use when creating the key object */ rc = pkcs_get_keytype(attrs, attrs_len, mech, &ktype, &class); @@ -3823,7 +4518,7 @@ if (rc != CKR_OK) { TRACE_ERROR("%s check secret key attributes failed: rc=0x%lx\n", __func__, rc); - return rc; + goto error; } rc = object_mgr_create_skel(tokdata, session, new_attrs, new_attrs_len, @@ -3834,20 +4529,32 @@ goto error; } - rc = build_ep11_attrs(tokdata, key_obj->template, &new_attrs2, &new_attrs2_len, ktype, CKO_SECRET_KEY, -1); + rc = build_ep11_attrs(tokdata, key_obj->template, + &new_attrs2, &new_attrs2_len, + ktype, CKO_SECRET_KEY, -1, mech); if (rc != CKR_OK) { TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto error; } + if (mech->mechanism == CKM_AES_XTS_KEY_GEN) { + xts = TRUE; + rc = ep11tok_pkey_check_aes_xts(tokdata, key_obj, mech->mechanism); + if (rc != CKR_OK) { + TRACE_ERROR("%s EP11 AES XTS is not supported: rc=0x%lx\n", + __func__, rc); + goto error; + } + } + trace_attributes(__func__, "Generate key:", new_attrs2, new_attrs2_len); ep11_get_pin_blob(ep11_session, ep11_is_session_object(attrs, attrs_len), &ep11_pin_blob, &ep11_pin_blob_len); RETRY_START(rc, tokdata) - rc = dll_m_GenerateKey(mech, new_attrs2, new_attrs2_len, ep11_pin_blob, - ep11_pin_blob_len, blob, &blobsize, + rc = dll_m_GenerateKey((xts ? &mech2 : mech), new_attrs2, new_attrs2_len, + ep11_pin_blob, ep11_pin_blob_len, blob, &blobsize, csum, &csum_len, target_info->target); RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { @@ -3855,12 +4562,52 @@ TRACE_ERROR("%s m_GenerateKey rc=0x%lx mech='%s' attrs_len=0x%lx\n", __func__, rc, ep11_get_ckm(tokdata, mech->mechanism), attrs_len); - goto done; + goto error; } TRACE_INFO("%s m_GenerateKey rc=0x%lx mech='%s' attrs_len=0x%lx\n", __func__, rc, ep11_get_ckm(tokdata, mech->mechanism), attrs_len); + if (check_expected_mkvp(tokdata, blob, blobsize) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + goto error; + } + + if (xts) { + RETRY_START(rc, tokdata) + rc = dll_m_GenerateKey(&mech2, new_attrs2, new_attrs2_len, + ep11_pin_blob, ep11_pin_blob_len, blob2, + &blobsize2, csum, &csum_len, + target_info->target); + RETRY_END(rc, tokdata, session) + if (rc != CKR_OK) { + rc = ep11_error_to_pkcs11_error(rc, session); + TRACE_ERROR("%s m_GenerateKey rc=0x%lx mech='%s' attrs_len=0x%lx\n", + __func__, rc, ep11_get_ckm(tokdata, mech->mechanism), + attrs_len); + goto error; + } + + TRACE_INFO("%s m_GenerateKey rc=0x%lx mech='%s' attrs_len=0x%lx\n", + __func__, rc, ep11_get_ckm(tokdata, mech->mechanism), attrs_len); + + if (check_expected_mkvp(tokdata, blob2, blobsize2) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + goto error; + } + + if (blobsize + blobsize2 > MAX_BLOBSIZE) { + TRACE_ERROR("%s\n", ock_err(CKR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + goto error; + } + + memcpy(blob + blobsize, blob2, blobsize2); + blobsize = blobsize + blobsize2; + } + rc = build_attribute(CKA_IBM_OPAQUE, blob, blobsize, &attr); if (rc != CKR_OK) { TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); @@ -3875,14 +4622,14 @@ } attr = NULL; - rc = update_ep11_attrs_from_blob(tokdata, key_obj->template); + rc = update_ep11_attrs_from_blob(tokdata, session, key_obj->template, xts); if (rc != CKR_OK) { TRACE_ERROR("%s update_ep11_attrs_from_blob failed with rc=0x%lx\n", __func__, rc); goto error; } - if (class == CKO_SECRET_KEY && csum_len >= EP11_CSUMSIZE) { + if (!xts && csum_len >= EP11_CSUMSIZE) { /* First 3 bytes of csum is the check value */ rc = build_attribute(CKA_CHECK_VALUE, csum, EP11_CSUMSIZE, &attr); if (rc != CKR_OK) { @@ -3904,8 +4651,8 @@ rc = build_attribute(CKA_KEY_GEN_MECHANISM, (CK_BYTE *)&mech->mechanism, sizeof(CK_MECHANISM_TYPE), &attr); if (rc != CKR_OK) { - TRACE_DEVEL("build_attribute failed\n"); - goto error; + TRACE_DEVEL("build_attribute failed\n"); + goto error; } rc = template_update_attribute(key_obj->template, attr); if (rc != CKR_OK) { @@ -4285,8 +5032,10 @@ } target_info = get_target_info(tokdata); - if (target_info == NULL) + if (target_info == NULL) { + free(state); return CKR_FUNCTION_FAILED; + } if (ep11tok_libica_digest_available(tokdata, ep11_data, mech->mechanism)) { libica_ctx = (libica_sha_context_t *)state; @@ -4830,7 +5579,285 @@ return rc; } -CK_RV ep11tok_derive_key(STDLL_TokData_t * tokdata, SESSION * session, +/** + * This routine is currently only used when the operation is performed using + * a protected key. Therefore we don't have (and don't need) an ep11 + * fallback here. + */ +CK_RV token_specific_aes_xts(STDLL_TokData_t *tokdata, + CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len, + OBJECT *key_obj, CK_BYTE *init_v, + CK_BBOOL encrypt, CK_BBOOL initial, + CK_BBOOL final, CK_BYTE *iv) +{ + UNUSED(tokdata); + return pkey_aes_xts(key_obj, init_v, in_data, in_data_len, + out_data, out_data_len, encrypt, initial, final, iv); +} + +struct EP11_KYBER_MECH { + CK_MECHANISM mech; + struct XCP_KYBER_KEM_PARAMS params; +}; + +static CK_RV ep11tok_kyber_mech_pre_process(STDLL_TokData_t *tokdata, + CK_MECHANISM *mech, + struct EP11_KYBER_MECH *mech_ep11, + OBJECT **secret_key_obj) +{ + CK_IBM_KYBER_PARAMS *kyber_params; + CK_RV rc; + + kyber_params = mech->pParameter; + if (mech->ulParameterLen != sizeof(CK_IBM_KYBER_PARAMS)) { + TRACE_ERROR("Mechanism parameter length not as expected\n"); + return CKR_MECHANISM_PARAM_INVALID; + } + + if (kyber_params->ulVersion != CK_IBM_KYBER_KEM_VERSION) { + TRACE_ERROR("Unsupported version in Kyber mechanism param\n"); + return CKR_MECHANISM_PARAM_INVALID; + } + + mech_ep11->mech.mechanism = mech->mechanism; + mech_ep11->mech.pParameter = &mech_ep11->params; + mech_ep11->mech.ulParameterLen = sizeof(mech_ep11->params); + + memset(&mech_ep11->params, 0, sizeof(mech_ep11->params)); + mech_ep11->params.version = XCP_KYBER_KEM_VERSION; + mech_ep11->params.mode = kyber_params->mode; + mech_ep11->params.kdf = kyber_params->kdf; + mech_ep11->params.prepend = kyber_params->bPrepend; + mech_ep11->params.pSharedData = kyber_params->pSharedData; + mech_ep11->params.ulSharedDataLen = kyber_params->ulSharedDataLen; + + switch (kyber_params->mode) { + case CK_IBM_KYBER_KEM_ENCAPSULATE: + if (kyber_params->ulCipherLen > 0 && kyber_params->pCipher == NULL) { + TRACE_ERROR("Unsupported cipher buffer in Kyber mechnism param " + "cannot be NULL\n"); + return CKR_MECHANISM_PARAM_INVALID; + } + + mech_ep11->params.pCipher = NULL; + mech_ep11->params.ulCipherLen = 0; + /* Cipher is returned in 2nd output param of m_DeriveKey */ + break; + + case CK_IBM_KEM_DECAPSULATE: + mech_ep11->params.pCipher = kyber_params->pCipher; + mech_ep11->params.ulCipherLen = kyber_params->ulCipherLen; + break; + + default: + TRACE_ERROR("Unsupported mode in Kyber mechanism param\n"); + return CKR_MECHANISM_PARAM_INVALID; + } + + if (kyber_params->bPrepend) { + rc = h_opaque_2_blob(tokdata, kyber_params->hSecret, + &mech_ep11->params.pBlob, + &mech_ep11->params.ulBlobLen, + secret_key_obj, READ_LOCK); + if (rc != CKR_OK) { + TRACE_ERROR("%s failed hSecret=0x%lx\n", __func__, + kyber_params->hSecret); + return rc; + } + } + + return CKR_OK; +} + +static CK_RV ep11tok_kyber_mech_post_process(STDLL_TokData_t *tokdata, + CK_MECHANISM *mech, + CK_BYTE *csum, CK_ULONG cslen) +{ + CK_IBM_KYBER_PARAMS *kyber_params; + CK_ULONG cipher_len; + + UNUSED(tokdata); + + kyber_params = mech->pParameter; + if (mech->ulParameterLen != sizeof(CK_IBM_KYBER_PARAMS)) { + TRACE_ERROR("Mechanism parameter length not as expected\n"); + return CKR_MECHANISM_PARAM_INVALID; + } + + if (kyber_params->mode != CK_IBM_KYBER_KEM_ENCAPSULATE) + return CKR_OK; + + /* + * For encapsulate: + * Generated cipher is returned in csum prepended with the checksum of + * the generated symmetric key and its bit count (in total 7 bytes). + */ + if (cslen < EP11_CSUMSIZE + 4) { + TRACE_ERROR("%s returned cipher size is invalid: %lu\n", + __func__, cslen); + return CKR_FUNCTION_FAILED; + } + + cipher_len = cslen - (EP11_CSUMSIZE + 4); + + if (kyber_params->ulCipherLen < cipher_len) { + TRACE_ERROR("%s Cipher buffer in kyber mechanism param too small, required: %lu\n", + __func__, cipher_len); + kyber_params->ulCipherLen = cipher_len; + OPENSSL_cleanse(&csum[EP11_CSUMSIZE + 4], cipher_len); + return CKR_BUFFER_TOO_SMALL; + } + + memcpy(kyber_params->pCipher, &csum[EP11_CSUMSIZE + 4], cipher_len); + kyber_params->ulCipherLen = cipher_len; + + OPENSSL_cleanse(&csum[EP11_CSUMSIZE + 4], cipher_len); + return CKR_OK; +} + +static CK_RV ep11tok_btc_mech_pre_process(STDLL_TokData_t *tokdata, + OBJECT *key_obj, + CK_ATTRIBUTE **new_attrs, + CK_ULONG *new_attrs_len) +{ + CK_ATTRIBUTE *ec_params; + CK_ULONG i, privlen; + CK_RV rc; + + UNUSED(tokdata); + + /* + * CKM_IBM_BTC_DERIVE requires CKA_VALUE_LEN to specify the byte length + * of the to be derived EC key. CKA_VALUE_LEN is dependent on the + * curve used. + * CKA_VALUE_LEN can not be already in the user supplied template, + * since this is not allowed by the key template check routines. + */ + rc = template_attribute_get_non_empty(key_obj->template, CKA_EC_PARAMS, + &ec_params); + if (rc != CKR_OK) { + TRACE_ERROR("CKA_EC_PARAMS is required in derive template\n"); + return rc; + } + + for (i = 0; i < NUMEC; i++) { + if (der_ec_supported[i].data_size == ec_params->ulValueLen && + memcmp(ec_params->pValue, der_ec_supported[i].data, + ec_params->ulValueLen) == 0) { + privlen = (der_ec_supported[i].len_bits + 7) / 8; + rc = add_to_attribute_array(new_attrs, new_attrs_len, + CKA_VALUE_LEN, + (CK_BYTE_PTR)&privlen, + sizeof(privlen)); + if (rc != CKR_OK) { + TRACE_ERROR("Adding attribute failed type=CKA_VALUE_LEN " + "rc=0x%lx\n", rc); + return rc; + } + break; + } + } + + return CKR_OK; +} + +static CK_RV ep11tok_btc_mech_post_process(STDLL_TokData_t *tokdata, + SESSION *session, CK_MECHANISM *mech, + CK_ULONG class, CK_ULONG ktype, + OBJECT *key_obj, + CK_BYTE *blob, CK_ULONG bloblen, + CK_BYTE *csum, CK_ULONG cslen) +{ + CK_IBM_BTC_DERIVE_PARAMS *btc_params = NULL; + CK_BYTE *spki = NULL; + CK_ULONG spki_length = 0; + CK_BYTE buf[MAX_BLOBSIZE]; + CK_ATTRIBUTE get_attr[1] = {{ CKA_PUBLIC_KEY_INFO, &buf, sizeof(buf) }}; + CK_ATTRIBUTE *spki_attr = NULL; + CK_BBOOL allocated = FALSE; + CK_RV rc = CKR_OK; + + if (mech->ulParameterLen != sizeof(CK_IBM_BTC_DERIVE_PARAMS) || + mech->pParameter == NULL) { + TRACE_ERROR("%s Param NULL or len for %s wrong: %lu\n", + __func__, ep11_get_ckm(tokdata, mech->mechanism), + mech->ulParameterLen); + return CKR_MECHANISM_PARAM_INVALID; + } + + btc_params = (CK_IBM_BTC_DERIVE_PARAMS *)mech->pParameter; + + if (btc_params != NULL && btc_params->pChainCode != NULL && + cslen >= CK_IBM_BTC_CHAINCODE_LENGTH) { + memcpy(btc_params->pChainCode, csum, CK_IBM_BTC_CHAINCODE_LENGTH); + btc_params->ulChainCodeLen = CK_IBM_BTC_CHAINCODE_LENGTH; + } + + switch (class) { + case CKO_PUBLIC_KEY: + /* Derived blob is an SPKI, extract public EC key attributes */ + rc = ecdsa_priv_unwrap_get_data(key_obj->template, blob, bloblen); + if (rc != CKR_OK) { + TRACE_ERROR("%s ecdsa_priv_unwrap_get_data failed with " + "rc=0x%lx\n", __func__, rc); + return rc; + } + + /* Extract the SPKI and add CKA_PUBLIC_KEY_INFO to key */ + rc = publ_key_get_spki(key_obj->template, ktype, FALSE, + &spki, &spki_length); + if (rc != CKR_OK) { + TRACE_DEVEL("publ_key_get_spki failed\n"); + return rc; + } + + allocated = TRUE; + break; + + case CKO_PRIVATE_KEY: + RETRY_START(rc, tokdata) + rc = dll_m_GetAttributeValue(blob, bloblen, get_attr, 1, + target_info->target); + RETRY_END(rc, tokdata, session) + + /* Only newer EP11 libs support this, ignore if error */ + if (rc != CKR_OK) + return CKR_OK; + + spki = get_attr[0].pValue; + spki_length = get_attr[0].ulValueLen; + break; + + default: + /* do nothing */ + return CKR_OK; + } + + rc = build_attribute(CKA_PUBLIC_KEY_INFO, spki, spki_length, + &spki_attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", + __func__, rc); + goto out; + } + + rc = template_update_attribute(key_obj->template, spki_attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(spki_attr); + goto out; + } + +out: + if (allocated && spki != NULL) + free(spki); + + return rc; +} + +CK_RV ep11tok_derive_key(STDLL_TokData_t *tokdata, SESSION *session, CK_MECHANISM_PTR mech, CK_OBJECT_HANDLE hBaseKey, CK_OBJECT_HANDLE_PTR handle, CK_ATTRIBUTE_PTR attrs, CK_ULONG attrs_len) @@ -4865,6 +5892,9 @@ ep11_target_info_t* target_info; CK_ULONG used_firmware_API_version; CK_MECHANISM_PTR mech_orig = mech; + struct EP11_KYBER_MECH mech_ep11; + OBJECT *kyber_secret_obj = NULL; + CK_KEY_TYPE keytype; memset(newblob, 0, sizeof(newblob)); @@ -4989,6 +6019,19 @@ TRACE_ERROR("%s failedL hBaseKey=0x%lx\n", __func__, hBaseKey); return rc; } + + rc = template_attribute_get_ulong(base_key_obj->template, CKA_KEY_TYPE, &keytype); + if (rc != CKR_OK) { + TRACE_ERROR("Invalid key type attribute\n"); + goto error; + } + + if (mech->mechanism == CKM_AES_XTS || keytype == CKK_AES_XTS) { + TRACE_ERROR("%s Key derive with AES-XTS is not supported\n", __func__); + rc = CKR_KEY_TYPE_INCONSISTENT; + goto error; + } + rc = tokdata->policy->is_mech_allowed(tokdata->policy, mech_orig, &base_key_obj->strength, POLICY_CHECK_DERIVE, @@ -5012,6 +6055,12 @@ goto error; } + if (ktype == CKK_AES_XTS) { + TRACE_ERROR("%s Deriving an AES-XTS key is not supported\n", __func__); + rc = CKR_KEY_TYPE_INCONSISTENT; + goto error; + } + rc = check_key_attributes(tokdata, ktype, class, attrs, attrs_len, &new_attrs, &new_attrs_len, -1); if (rc != CKR_OK) { @@ -5094,25 +6143,51 @@ curve_type = get_curve_type_from_template(key_obj->template); rc = build_ep11_attrs(tokdata, key_obj->template, &new_attrs2, &new_attrs2_len, - ktype, class, curve_type); + ktype, class, curve_type, mech); if (rc != CKR_OK) { TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto error; } + switch (mech->mechanism) { + case CKM_IBM_BTC_DERIVE: + rc = ep11tok_btc_mech_pre_process(tokdata, key_obj, &new_attrs2, + &new_attrs2_len); + if (rc != CKR_OK) + goto error; + break; + + case CKM_IBM_KYBER: + rc = ep11tok_kyber_mech_pre_process(tokdata, mech, &mech_ep11, + &kyber_secret_obj); + if (rc != CKR_OK) + goto error; + mech = &mech_ep11.mech; + break; + + default: + break; + } + trace_attributes(__func__, "Derive:", new_attrs2, new_attrs2_len); ep11_get_pin_blob(ep11_session, ep11_is_session_object(attrs, attrs_len), &ep11_pin_blob, &ep11_pin_blob_len); RETRY_START(rc, tokdata) - rc = - dll_m_DeriveKey(mech, new_attrs2, new_attrs2_len, keyblob, keyblobsize, - NULL, 0, ep11_pin_blob, ep11_pin_blob_len, newblob, - &newblobsize, csum, &cslen, target_info->target); + if (ep11_pqc_obj_strength_supported(target_info, mech->mechanism, + base_key_obj)) + rc = dll_m_DeriveKey(mech, new_attrs2, new_attrs2_len, + keyblob, keyblobsize, NULL, 0, + ep11_pin_blob, ep11_pin_blob_len, newblob, + &newblobsize, csum, &cslen, + target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { + rc = ep11_error_to_pkcs11_error(rc, session); TRACE_ERROR("%s hBaseKey=0x%lx rc=0x%lx handle=0x%lx blobsize=0x%zx\n", __func__, hBaseKey, rc, *handle, newblobsize); goto error; @@ -5120,6 +6195,13 @@ TRACE_INFO("%s hBaseKey=0x%lx rc=0x%lx handle=0x%lx blobsize=0x%zx\n", __func__, hBaseKey, rc, *handle, newblobsize); + if (class == CKO_SECRET_KEY || class == CKO_PRIVATE_KEY) { + if (check_expected_mkvp(tokdata, newblob, newblobsize) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + goto error; + } + } rc = build_attribute(CKA_IBM_OPAQUE, newblob, newblobsize, &opaque_attr); if (rc != CKR_OK) { @@ -5135,11 +6217,32 @@ } opaque_attr = NULL; - rc = update_ep11_attrs_from_blob(tokdata, key_obj->template); - if (rc != CKR_OK) { - TRACE_ERROR("%s update_ep11_attrs_from_blob failed with rc=0x%lx\n", - __func__, rc); - goto error; + if (class == CKO_SECRET_KEY || class == CKO_PRIVATE_KEY) { + rc = update_ep11_attrs_from_blob(tokdata, session, key_obj->template, FALSE); + if (rc != CKR_OK) { + TRACE_ERROR("%s update_ep11_attrs_from_blob failed with rc=0x%lx\n", + __func__, rc); + goto error; + } + } + + switch (mech->mechanism) { + case CKM_IBM_BTC_DERIVE: + rc = ep11tok_btc_mech_post_process(tokdata, session, mech, class, ktype, + key_obj, newblob, newblobsize, + csum, cslen); + if (rc != CKR_OK) + goto error; + break; + + case CKM_IBM_KYBER: + rc = ep11tok_kyber_mech_post_process(tokdata, mech_orig, csum, cslen); + if (rc != CKR_OK) + goto error; + break; + + default: + break; } if (class == CKO_SECRET_KEY && cslen >= EP11_CSUMSIZE) { @@ -5194,21 +6297,18 @@ object_put(tokdata, base_key_obj, TRUE); base_key_obj = NULL; + object_put(tokdata, kyber_secret_obj, TRUE); + kyber_secret_obj = NULL; return rc; } -static CK_RV dh_generate_keypair(STDLL_TokData_t * tokdata, - SESSION * sess, +static CK_RV dh_generate_keypair(STDLL_TokData_t *tokdata, + SESSION *sess, CK_MECHANISM_PTR pMechanism, - TEMPLATE * publ_tmpl, TEMPLATE * priv_tmpl, - CK_ATTRIBUTE_PTR pPublicKeyTemplate, - CK_ULONG ulPublicKeyAttributeCount, - CK_ATTRIBUTE_PTR pPrivateKeyTemplate, - CK_ULONG ulPrivateKeyAttributeCount, - CK_SESSION_HANDLE h) + TEMPLATE *publ_tmpl, TEMPLATE *priv_tmpl) { CK_RV rc; CK_BYTE publblob[MAX_BLOBSIZE]; @@ -5220,19 +6320,15 @@ CK_ATTRIBUTE *opaque_attr = NULL; CK_ATTRIBUTE *value_attr = NULL; CK_ATTRIBUTE *attr = NULL; - CK_ATTRIBUTE *pPublicKeyTemplate_new = NULL; CK_ATTRIBUTE_PTR dh_pPublicKeyTemplate = NULL; CK_ULONG dh_ulPublicKeyAttributeCount = 0; CK_ATTRIBUTE_PTR dh_pPrivateKeyTemplate = NULL; CK_ULONG dh_ulPrivateKeyAttributeCount = 0; - size_t p_len = 0, g_len = 0; - int new_public_attr; - CK_ULONG i; CK_ULONG data_len; CK_ULONG field_len; CK_BYTE *data; CK_BYTE *y_start, *oid, *parm; - CK_ULONG bit_str_len, oid_len, parm_len; + CK_ULONG bit_str_len, oid_len, parm_len, value_bits = 0; unsigned char *ep11_pin_blob = NULL; CK_ULONG ep11_pin_blob_len = 0; ep11_session_t *ep11_session = (ep11_session_t *) sess->private_data; @@ -5247,145 +6343,122 @@ unsigned char *pg; } dh_pgs; - UNUSED(h); - memset(&dh_pgs, 0, sizeof(dh_pgs)); memset(publblob, 0, sizeof(publblob)); memset(privblob, 0, sizeof(privblob)); - /* card does not want CKA_PRIME/CKA_BASE in template but in dh_pgs */ - pPublicKeyTemplate_new = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) * - ulPublicKeyAttributeCount); - if (!pPublicKeyTemplate_new) { - TRACE_ERROR("%s Memory allocation failed\n", __func__); - return CKR_HOST_MEMORY; - } - memset(pPublicKeyTemplate_new, 0, - sizeof(CK_ATTRIBUTE) * ulPublicKeyAttributeCount); - - for (i = 0, new_public_attr = 0; i < ulPublicKeyAttributeCount; i++) { - /* filter out CKA_PRIME/CKA_BASE, - * but remember where they can be found - */ - switch (pPublicKeyTemplate[i].type) { - case CKA_PRIME: - prime_attr = &(pPublicKeyTemplate[i]); - p_len = pPublicKeyTemplate[i].ulValueLen; - break; - case CKA_BASE: - base_attr = &(pPublicKeyTemplate[i]); - g_len = pPublicKeyTemplate[i].ulValueLen; - break; - default: - /* copy all other attributes */ - memcpy(&pPublicKeyTemplate_new[new_public_attr], - &(pPublicKeyTemplate[i]), sizeof(CK_ATTRIBUTE)); - new_public_attr++; - } + rc = build_ep11_attrs(tokdata, publ_tmpl, &dh_pPublicKeyTemplate, + &dh_ulPublicKeyAttributeCount, + CKK_DH, CKO_PUBLIC_KEY, -1, pMechanism); + if (rc != CKR_OK) { + TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); + goto dh_generate_keypair_end; } - if (prime_attr == NULL || base_attr == NULL) { - TRACE_ERROR("%s Incomplete template prime_attr=%p base_attr=%p\n", - __func__, (void *)prime_attr, (void *)base_attr); - rc = CKR_TEMPLATE_INCOMPLETE; + rc = build_ep11_attrs(tokdata, priv_tmpl, &dh_pPrivateKeyTemplate, + &dh_ulPrivateKeyAttributeCount, + CKK_DH, CKO_PRIVATE_KEY, -1, pMechanism); + if (rc != CKR_OK) { + TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto dh_generate_keypair_end; } - /* copy CKA_PRIME/CKA_BASE to private template */ - rc = build_attribute(CKA_PRIME, prime_attr->pValue, - prime_attr->ulValueLen, &attr); + rc = check_key_attributes(tokdata, CKK_DH, CKO_PUBLIC_KEY, + dh_pPublicKeyTemplate, + dh_ulPublicKeyAttributeCount, + &new_publ_attrs, &new_publ_attrs_len, -1); if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s DH check public key attributes failed with " + "rc=0x%lx\n", __func__, rc); goto dh_generate_keypair_end; } - rc = template_update_attribute(priv_tmpl, attr); + + rc = check_key_attributes(tokdata, CKK_DH, CKO_PRIVATE_KEY, + dh_pPrivateKeyTemplate, + dh_ulPrivateKeyAttributeCount, + &new_priv_attrs, &new_priv_attrs_len, -1); if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); + TRACE_ERROR("%s DH check private key attributes failed with " + "rc=0x%lx\n", __func__, rc); goto dh_generate_keypair_end; } - rc = build_attribute(CKA_BASE, base_attr->pValue, - base_attr->ulValueLen, &attr); + + /* card does not want CKA_PRIME/CKA_BASE in template but in dh_pgs */ + rc = template_attribute_get_non_empty(publ_tmpl, CKA_PRIME, + &prime_attr); if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s DH No CKA_PRIME attribute found\n", __func__); goto dh_generate_keypair_end; } - rc = template_update_attribute(priv_tmpl, attr); + + rc = template_attribute_get_non_empty(publ_tmpl, CKA_BASE, + &base_attr); if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); + TRACE_ERROR("%s DH No CKA_BASE attribute found\n", __func__); goto dh_generate_keypair_end; } - /* copy CKA_PRIME/CKA_BASE values */ - dh_pgs.pg = malloc(p_len * 2); + dh_pgs.pg = malloc(prime_attr->ulValueLen * 2); if (!dh_pgs.pg) { TRACE_ERROR("%s Memory allocation failed\n", __func__); rc = CKR_HOST_MEMORY; goto dh_generate_keypair_end; } - memset(dh_pgs.pg, 0, p_len * 2); - memcpy(dh_pgs.pg, prime_attr->pValue, p_len); /* copy CKA_PRIME value */ + + memset(dh_pgs.pg, 0, prime_attr->ulValueLen * 2); + /* copy CKA_PRIME value */ + memcpy(dh_pgs.pg, prime_attr->pValue, prime_attr->ulValueLen); /* copy CKA_BASE value, it must have leading zeros * if it is shorter than CKA_PRIME */ - memcpy(dh_pgs.pg + p_len + (p_len - g_len), base_attr->pValue, g_len); - dh_pgs.pg_bytes = p_len * 2; + memcpy(dh_pgs.pg + prime_attr->ulValueLen + + (prime_attr->ulValueLen - base_attr->ulValueLen), + base_attr->pValue, base_attr->ulValueLen); + dh_pgs.pg_bytes = prime_attr->ulValueLen * 2; #ifdef DEBUG TRACE_DEBUG("%s P:\n", __func__); - TRACE_DEBUG_DUMP(" ", &dh_pgs.pg[0], p_len); + TRACE_DEBUG_DUMP(" ", &dh_pgs.pg[0], prime_attr->ulValueLen); TRACE_DEBUG("%s G:\n", __func__); - TRACE_DEBUG_DUMP(" ", &dh_pgs.pg[p_len], p_len); + TRACE_DEBUG_DUMP(" ", &dh_pgs.pg[prime_attr->ulValueLen], + prime_attr->ulValueLen); #endif - /* add special attribute, do not add it to ock's pPublicKeyTemplate */ - CK_ATTRIBUTE pgs[] = { {CKA_IBM_STRUCT_PARAMS, (CK_VOID_PTR) dh_pgs.pg, - dh_pgs.pg_bytes} - }; - memcpy(&(pPublicKeyTemplate_new[new_public_attr]), - &(pgs[0]), sizeof(CK_ATTRIBUTE)); - - rc = check_key_attributes(tokdata, CKK_DH, CKO_PUBLIC_KEY, - pPublicKeyTemplate_new, new_public_attr + 1, - &dh_pPublicKeyTemplate, - &dh_ulPublicKeyAttributeCount, -1); + rc = add_to_attribute_array(&new_publ_attrs, &new_publ_attrs_len, + CKA_IBM_STRUCT_PARAMS, dh_pgs.pg, + dh_pgs.pg_bytes); if (rc != CKR_OK) { - TRACE_ERROR("%s DH check public key attributes failed with " - "rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s add_to_attribute_array failed with rc=0x%lx\n", + __func__, rc); goto dh_generate_keypair_end; } - rc = check_key_attributes(tokdata, CKK_DH, CKO_PRIVATE_KEY, - pPrivateKeyTemplate, ulPrivateKeyAttributeCount, - &dh_pPrivateKeyTemplate, - &dh_ulPrivateKeyAttributeCount, -1); + /* copy CKA_PRIME/CKA_BASE to private template */ + rc = build_attribute(CKA_PRIME, prime_attr->pValue, + prime_attr->ulValueLen, &attr); if (rc != CKR_OK) { - TRACE_ERROR("%s DH check private key attributes failed with " - "rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); goto dh_generate_keypair_end; } - - rc = build_ep11_attrs(tokdata, publ_tmpl, &new_publ_attrs, &new_publ_attrs_len, CKK_DH, CKO_PUBLIC_KEY, -1); + rc = template_update_attribute(priv_tmpl, attr); if (rc != CKR_OK) { - TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(attr); goto dh_generate_keypair_end; } - rc = add_to_attribute_array(&new_publ_attrs, &new_publ_attrs_len, - CKA_IBM_STRUCT_PARAMS, (CK_VOID_PTR) dh_pgs.pg, - dh_pgs.pg_bytes); + rc = build_attribute(CKA_BASE, base_attr->pValue, + base_attr->ulValueLen, &attr); if (rc != CKR_OK) { - TRACE_ERROR("%s add_to_attribute_array failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); goto dh_generate_keypair_end; } - - rc = build_ep11_attrs(tokdata, priv_tmpl, &new_priv_attrs, &new_priv_attrs_len, CKK_DH, CKO_PRIVATE_KEY, -1); + rc = template_update_attribute(priv_tmpl, attr); if (rc != CKR_OK) { - TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(attr); goto dh_generate_keypair_end; } @@ -5395,10 +6468,10 @@ new_priv_attrs, new_priv_attrs_len); ep11_get_pin_blob(ep11_session, - (ep11_is_session_object - (pPublicKeyTemplate, ulPublicKeyAttributeCount) - || ep11_is_session_object(pPrivateKeyTemplate, - ulPrivateKeyAttributeCount)), + (ep11_is_session_object(new_publ_attrs, + new_publ_attrs_len) || + ep11_is_session_object(new_priv_attrs, + new_priv_attrs_len)), &ep11_pin_blob, &ep11_pin_blob_len); RETRY_START(rc, tokdata) @@ -5417,7 +6490,13 @@ } TRACE_INFO("%s rc=0x%lx plen=%zd publblobsize=0x%zx privblobsize=0x%zx\n", - __func__, rc, p_len, publblobsize, privblobsize); + __func__, rc, prime_attr->ulValueLen, publblobsize, privblobsize); + + if (check_expected_mkvp(tokdata, privblob, privblobsize) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + goto dh_generate_keypair_end; + } /* store the blobs */ rc = build_attribute(CKA_IBM_OPAQUE, publblob, publblobsize, &opaque_attr); @@ -5499,8 +6578,29 @@ goto dh_generate_keypair_end; } + /* Supply CKA_VALUE_BITS to private key if not present or zero */ + if (template_attribute_get_ulong(priv_tmpl, CKA_VALUE_BITS, + &value_bits) != CKR_OK || + value_bits == 0) { + value_bits = data_len * 8; /* private key is same length as pub key */ + + rc = build_attribute(CKA_VALUE_BITS, (CK_BYTE *)&data_len, + sizeof(value_bits), &value_attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); + goto dh_generate_keypair_end; + } + + rc = template_update_attribute(priv_tmpl, value_attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(value_attr); + goto dh_generate_keypair_end; + } + } + dh_generate_keypair_end: - free(pPublicKeyTemplate_new); if (dh_pgs.pg != NULL) free(dh_pgs.pg); if (dh_pPublicKeyTemplate) @@ -5516,15 +6616,10 @@ return rc; } -static CK_RV dsa_generate_keypair(STDLL_TokData_t * tokdata, - SESSION * sess, +static CK_RV dsa_generate_keypair(STDLL_TokData_t *tokdata, + SESSION *sess, CK_MECHANISM_PTR pMechanism, - TEMPLATE * publ_tmpl, TEMPLATE * priv_tmpl, - CK_ATTRIBUTE_PTR pPublicKeyTemplate, - CK_ULONG ulPublicKeyAttributeCount, - CK_ATTRIBUTE_PTR pPrivateKeyTemplate, - CK_ULONG ulPrivateKeyAttributeCount, - CK_SESSION_HANDLE h) + TEMPLATE *publ_tmpl, TEMPLATE *priv_tmpl) { CK_RV rc; CK_BYTE publblob[MAX_BLOBSIZE]; @@ -5537,10 +6632,6 @@ CK_ATTRIBUTE *opaque_attr = NULL; CK_ATTRIBUTE *value_attr = NULL; CK_ATTRIBUTE *attr = NULL; - size_t p_len = 0, q_len = 0, g_len = 0; - int new_public_attr; - CK_ULONG i; - CK_ATTRIBUTE *pPublicKeyTemplate_new = NULL; CK_BYTE *key; CK_BYTE *data, *oid, *parm; CK_ULONG data_len, field_len, bit_str_len, oid_len, parm_len; @@ -5553,8 +6644,6 @@ ep11_session_t *ep11_session = (ep11_session_t *) sess->private_data; CK_ATTRIBUTE *new_publ_attrs = NULL, *new_priv_attrs = NULL; CK_ULONG new_publ_attrs_len = 0, new_priv_attrs_len = 0; - CK_ATTRIBUTE *new_publ_attrs2 = NULL, *new_priv_attrs2 = NULL; - CK_ULONG new_publ_attrs2_len = 0, new_priv_attrs2_len = 0; /* ep11 accepts CKA_PRIME,CKA_SUBPRIME,CKA_BASE only in this format */ struct { @@ -5562,95 +6651,68 @@ unsigned char *pqg; } dsa_pqgs; - UNUSED(h); - memset(&dsa_pqgs, 0, sizeof(dsa_pqgs)); memset(publblob, 0, sizeof(publblob)); memset(privblob, 0, sizeof(privblob)); - /* card does not want CKA_PRIME/CKA_BASE/CKA_SUBPRIME - * in template but in dsa_pqgs - */ - pPublicKeyTemplate_new = - (CK_ATTRIBUTE *) malloc(sizeof(CK_ATTRIBUTE) * - ulPublicKeyAttributeCount); - if (!pPublicKeyTemplate_new) { - TRACE_ERROR("%s Memory allocation failed\n", __func__); - return CKR_HOST_MEMORY; - } - memset(pPublicKeyTemplate_new, 0, - sizeof(CK_ATTRIBUTE) * ulPublicKeyAttributeCount); - - for (i = 0, new_public_attr = 0; i < ulPublicKeyAttributeCount; i++) { - switch (pPublicKeyTemplate[i].type) { - case CKA_PRIME: - prime_attr = &(pPublicKeyTemplate[i]); - p_len = pPublicKeyTemplate[i].ulValueLen; - break; - case CKA_SUBPRIME: - sub_prime_attr = &(pPublicKeyTemplate[i]); - q_len = pPublicKeyTemplate[i].ulValueLen; - break; - case CKA_BASE: - base_attr = &(pPublicKeyTemplate[i]); - g_len = pPublicKeyTemplate[i].ulValueLen; - break; - default: - /* copy all other attributes */ - memcpy(&pPublicKeyTemplate_new[new_public_attr], - &(pPublicKeyTemplate[i]), sizeof(CK_ATTRIBUTE)); - new_public_attr++; - } - } - - if (prime_attr == NULL || sub_prime_attr == NULL || base_attr == NULL) { - rc = CKR_TEMPLATE_INCOMPLETE; + rc = build_ep11_attrs(tokdata, publ_tmpl, &dsa_pPublicKeyTemplate, + &dsa_ulPublicKeyAttributeCount, + CKK_DSA, CKO_PUBLIC_KEY, -1, pMechanism); + if (rc != CKR_OK) { + TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto dsa_generate_keypair_end; } - /* copy CKA_PRIME/CKA_BASE/CKA_SUBPRIME to private template */ - rc = build_attribute(CKA_PRIME, prime_attr->pValue, - prime_attr->ulValueLen, &attr); + rc = build_ep11_attrs(tokdata, priv_tmpl, &dsa_pPrivateKeyTemplate, + &dsa_ulPrivateKeyAttributeCount, + CKK_DSA, CKO_PRIVATE_KEY, -1, pMechanism); if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto dsa_generate_keypair_end; } - rc = template_update_attribute(priv_tmpl, attr); + rc = check_key_attributes(tokdata, CKK_DSA, CKO_PUBLIC_KEY, + dsa_pPublicKeyTemplate, + dsa_ulPublicKeyAttributeCount, + &new_publ_attrs, &new_publ_attrs_len, -1); if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); + TRACE_ERROR("%s DSA check public key attributes failed with " + "rc=0x%lx\n", __func__, rc); goto dsa_generate_keypair_end; } - rc = build_attribute(CKA_BASE, base_attr->pValue, - base_attr->ulValueLen, &attr); + rc = check_key_attributes(tokdata, CKK_DSA, CKO_PRIVATE_KEY, + dsa_pPrivateKeyTemplate, + dsa_ulPrivateKeyAttributeCount, + &new_priv_attrs, &new_priv_attrs_len, -1); if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s DSA check private key attributes failed with " + "rc=0x%lx\n", __func__, rc); goto dsa_generate_keypair_end; } - rc = template_update_attribute(priv_tmpl, attr); + /* + * card does not want CKA_PRIME/CKA_BASE/CKA_SUBPRIME in template but in + * dsa_pqgs + */ + rc = template_attribute_get_non_empty(publ_tmpl, CKA_PRIME, + &prime_attr); if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); + TRACE_ERROR("%s DSA No CKA_PRIME attribute found\n", __func__); goto dsa_generate_keypair_end; } - rc = build_attribute(CKA_SUBPRIME, sub_prime_attr->pValue, - sub_prime_attr->ulValueLen, &attr); + rc = template_attribute_get_non_empty(publ_tmpl, CKA_SUBPRIME, + &sub_prime_attr); if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s DSA No CKA_SUBPRIME attribute found\n", __func__); goto dsa_generate_keypair_end; } - rc = template_update_attribute(priv_tmpl, attr); + rc = template_attribute_get_non_empty(publ_tmpl, CKA_BASE, + &base_attr); if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); + TRACE_ERROR("%s DSA No CKA_BASE attribute found\n", __func__); goto dsa_generate_keypair_end; } @@ -5658,91 +6720,102 @@ * then they are extented by leading zeros till they have * the size of CKA_PRIME */ - dsa_pqgs.pqg = malloc(p_len * 3); + dsa_pqgs.pqg = malloc(prime_attr->ulValueLen * 3); if (!dsa_pqgs.pqg) { TRACE_ERROR("%s Memory allocation failed\n", __func__); rc = CKR_HOST_MEMORY; goto dsa_generate_keypair_end; } - memset(dsa_pqgs.pqg, 0, p_len * 3); - memcpy(dsa_pqgs.pqg, prime_attr->pValue, p_len); - memcpy(dsa_pqgs.pqg + p_len + (p_len - q_len), - sub_prime_attr->pValue, q_len); - memcpy(dsa_pqgs.pqg + 2 * p_len + (p_len - g_len), - base_attr->pValue, g_len); - dsa_pqgs.pqg_bytes = p_len * 3; + + memset(dsa_pqgs.pqg, 0, prime_attr->ulValueLen * 3); + memcpy(dsa_pqgs.pqg, prime_attr->pValue, prime_attr->ulValueLen); + memcpy(dsa_pqgs.pqg + prime_attr->ulValueLen + + (prime_attr->ulValueLen - sub_prime_attr->ulValueLen), + sub_prime_attr->pValue, sub_prime_attr->ulValueLen); + memcpy(dsa_pqgs.pqg + 2 * prime_attr->ulValueLen + + (prime_attr->ulValueLen - base_attr->ulValueLen), + base_attr->pValue, base_attr->ulValueLen); + dsa_pqgs.pqg_bytes = prime_attr->ulValueLen * 3; #ifdef DEBUG TRACE_DEBUG("%s P:\n", __func__); - TRACE_DEBUG_DUMP(" ", &dsa_pqgs.pqg[0], p_len); + TRACE_DEBUG_DUMP(" ", &dsa_pqgs.pqg[0], prime_attr->ulValueLen); TRACE_DEBUG("%s Q:\n", __func__); - TRACE_DEBUG_DUMP(" ", &dsa_pqgs.pqg[p_len], p_len); + TRACE_DEBUG_DUMP(" ", &dsa_pqgs.pqg[prime_attr->ulValueLen], + prime_attr->ulValueLen); TRACE_DEBUG("%s G:\n", __func__); - TRACE_DEBUG_DUMP(" ", &dsa_pqgs.pqg[2 * p_len], p_len); + TRACE_DEBUG_DUMP(" ", &dsa_pqgs.pqg[2 * prime_attr->ulValueLen], + prime_attr->ulValueLen); #endif - CK_ATTRIBUTE pqgs[] = { {CKA_IBM_STRUCT_PARAMS, - (CK_VOID_PTR) dsa_pqgs.pqg, dsa_pqgs.pqg_bytes} - }; - - /* add special attribute, do not add it to ock's pPublicKeyTemplate */ - memcpy(&(pPublicKeyTemplate_new[new_public_attr]), - &(pqgs[0]), sizeof(CK_ATTRIBUTE)); - - rc = build_ep11_attrs(tokdata, publ_tmpl, &new_publ_attrs, &new_publ_attrs_len, CKK_DSA, CKO_PUBLIC_KEY, -1); + rc = add_to_attribute_array(&new_publ_attrs, &new_publ_attrs_len, + CKA_IBM_STRUCT_PARAMS, dsa_pqgs.pqg, + dsa_pqgs.pqg_bytes); if (rc != CKR_OK) { - TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s add_to_attribute_array failed with rc=0x%lx\n", + __func__, rc); goto dsa_generate_keypair_end; } - rc = check_key_attributes(tokdata, CKK_DSA, CKO_PUBLIC_KEY, - new_publ_attrs, new_publ_attrs_len, - &new_publ_attrs2, &new_publ_attrs2_len, -1); + /* copy CKA_PRIME/CKA_BASE/CKA_SUBPRIME to private template */ + rc = build_attribute(CKA_PRIME, prime_attr->pValue, + prime_attr->ulValueLen, &attr); if (rc != CKR_OK) { - TRACE_ERROR("%s DSA check public key attributes failed with " - "rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); goto dsa_generate_keypair_end; } - - rc = add_to_attribute_array(&new_publ_attrs2, &new_publ_attrs2_len, - CKA_IBM_STRUCT_PARAMS, (CK_VOID_PTR) dsa_pqgs.pqg, - dsa_pqgs.pqg_bytes); + rc = template_update_attribute(priv_tmpl, attr); if (rc != CKR_OK) { - TRACE_ERROR("%s add_to_attribute_array failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(attr); goto dsa_generate_keypair_end; } - rc = build_ep11_attrs(tokdata, priv_tmpl, &new_priv_attrs, &new_priv_attrs_len, CKK_DSA, CKO_PRIVATE_KEY, -1); + rc = build_attribute(CKA_SUBPRIME, sub_prime_attr->pValue, + sub_prime_attr->ulValueLen, &attr); if (rc != CKR_OK) { - TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); + goto dsa_generate_keypair_end; + } + rc = template_update_attribute(priv_tmpl, attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(attr); goto dsa_generate_keypair_end; } - rc = check_key_attributes(tokdata, CKK_DSA, CKO_PRIVATE_KEY, - new_priv_attrs, new_priv_attrs_len, - &new_priv_attrs2, &new_priv_attrs2_len, -1); + rc = build_attribute(CKA_BASE, base_attr->pValue, + base_attr->ulValueLen, &attr); if (rc != CKR_OK) { - TRACE_ERROR("%s DSA check private key attributes failed with " - "rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); + goto dsa_generate_keypair_end; + } + rc = template_update_attribute(priv_tmpl, attr); + if (rc != CKR_OK) { + TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", + __func__, rc); + free(attr); goto dsa_generate_keypair_end; } trace_attributes(__func__, "DSA public key attributes:", - new_publ_attrs2, new_publ_attrs2_len); + new_publ_attrs, new_publ_attrs_len); trace_attributes(__func__, "DSA private key attributes:", - new_priv_attrs2, new_priv_attrs2_len); + new_priv_attrs, new_priv_attrs_len); ep11_get_pin_blob(ep11_session, - (ep11_is_session_object - (pPublicKeyTemplate, ulPublicKeyAttributeCount) - || ep11_is_session_object(pPrivateKeyTemplate, - ulPrivateKeyAttributeCount)), + (ep11_is_session_object(new_publ_attrs, + new_publ_attrs_len) || + ep11_is_session_object(new_priv_attrs, + new_priv_attrs_len)), &ep11_pin_blob, &ep11_pin_blob_len); RETRY_START(rc, tokdata) rc = dll_m_GenerateKeyPair(pMechanism, - new_publ_attrs2, new_publ_attrs2_len, - new_priv_attrs2, new_priv_attrs2_len, + new_publ_attrs, new_publ_attrs_len, + new_priv_attrs, new_priv_attrs_len, ep11_pin_blob, ep11_pin_blob_len, privblob, &privblobsize, publblob, &publblobsize, target_info->target); @@ -5755,10 +6828,14 @@ goto dsa_generate_keypair_end; } - TRACE_INFO("%s rc=0x%lx p_len=%zd publblobsize=0x%zx privblobsize=0x%zx " - "npattr=0x%x\n", - __func__, rc, p_len, publblobsize, privblobsize, - new_public_attr + 1); + TRACE_INFO("%s rc=0x%lx plen=%zd publblobsize=0x%zx privblobsize=0x%zx\n", + __func__, rc, prime_attr->ulValueLen, publblobsize, privblobsize); + + if (check_expected_mkvp(tokdata, privblob, privblobsize) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + goto dsa_generate_keypair_end; + } rc = build_attribute(CKA_IBM_OPAQUE, publblob, publblobsize, &opaque_attr); if (rc != CKR_OK) { @@ -5823,7 +6900,6 @@ } dsa_generate_keypair_end: - free(pPublicKeyTemplate_new); if (dsa_pqgs.pqg != NULL) free(dsa_pqgs.pqg); if (dsa_pPublicKeyTemplate) @@ -5836,22 +6912,13 @@ free_attribute_array(new_publ_attrs, new_publ_attrs_len); if (new_priv_attrs) free_attribute_array(new_priv_attrs, new_priv_attrs_len); - if (new_publ_attrs2) - free_attribute_array(new_publ_attrs2, new_publ_attrs2_len); - if (new_priv_attrs) - free_attribute_array(new_priv_attrs2, new_priv_attrs2_len); return rc; } -static CK_RV rsa_ec_generate_keypair(STDLL_TokData_t * tokdata, - SESSION * sess, +static CK_RV rsa_ec_generate_keypair(STDLL_TokData_t *tokdata, + SESSION *sess, CK_MECHANISM_PTR pMechanism, - TEMPLATE * publ_tmpl, TEMPLATE * priv_tmpl, - CK_ATTRIBUTE_PTR pPublicKeyTemplate, - CK_ULONG ulPublicKeyAttributeCount, - CK_ATTRIBUTE_PTR pPrivateKeyTemplate, - CK_ULONG ulPrivateKeyAttributeCount, - CK_SESSION_HANDLE h) + TEMPLATE *publ_tmpl, TEMPLATE *priv_tmpl) { CK_RV rc; CK_ATTRIBUTE *attr = NULL; @@ -5860,16 +6927,11 @@ size_t privkey_blob_len = sizeof(privkey_blob); unsigned char spki[MAX_BLOBSIZE]; size_t spki_len = sizeof(spki); - CK_ULONG i; CK_ULONG bit_str_len; CK_BYTE *key; CK_BYTE *data, *oid, *parm; CK_ULONG data_len, oid_len, parm_len; CK_ULONG field_len; - CK_ATTRIBUTE_PTR new_pPublicKeyTemplate = NULL; - CK_ULONG new_ulPublicKeyAttributeCount = 0; - CK_ATTRIBUTE_PTR new_pPrivateKeyTemplate = NULL; - CK_ULONG new_ulPrivateKeyAttributeCount = 0; CK_ULONG ktype; unsigned char *ep11_pin_blob = NULL; CK_ULONG ep11_pin_blob_len = 0; @@ -5880,8 +6942,6 @@ CK_ULONG new_publ_attrs2_len = 0, new_priv_attrs2_len = 0; const struct _ec *curve = NULL; - UNUSED(h); - if (pMechanism->mechanism == CKM_EC_KEY_PAIR_GEN) { ktype = CKK_EC; } else if ((pMechanism->mechanism == CKM_RSA_PKCS_KEY_PAIR_GEN) || @@ -5903,7 +6963,7 @@ rc = build_ep11_attrs(tokdata, publ_tmpl, &new_publ_attrs, &new_publ_attrs_len, ktype, CKO_PUBLIC_KEY, - curve != NULL ? curve->curve_type : -1); + curve != NULL ? curve->curve_type : -1, pMechanism); if (rc != CKR_OK) { TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto error; @@ -5912,7 +6972,7 @@ rc = build_ep11_attrs(tokdata, priv_tmpl, &new_priv_attrs, &new_priv_attrs_len, ktype, CKO_PRIVATE_KEY, - curve != NULL ? curve->curve_type : -1); + curve != NULL ? curve->curve_type : -1, pMechanism); if (rc != CKR_OK) { TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto error; @@ -5938,24 +6998,16 @@ goto error; } - /* debug */ - for (i = 0; i < new_ulPrivateKeyAttributeCount; i++) { - TRACE_INFO("%s gen priv attr type=0x%lx valuelen=0x%lx attrcnt=0x%lx\n", - __func__, new_pPrivateKeyTemplate[i].type, - new_pPrivateKeyTemplate[i].ulValueLen, - new_ulPrivateKeyAttributeCount); - } - trace_attributes(__func__, "RSA/EC public key attributes:", new_publ_attrs2, new_publ_attrs2_len); trace_attributes(__func__, "RSA/EC private key attributes:", new_priv_attrs2, new_priv_attrs2_len); ep11_get_pin_blob(ep11_session, - (ep11_is_session_object - (pPublicKeyTemplate, ulPublicKeyAttributeCount) - || ep11_is_session_object(pPrivateKeyTemplate, - ulPrivateKeyAttributeCount)), + (ep11_is_session_object(new_publ_attrs2, + new_publ_attrs2_len) || + ep11_is_session_object(new_priv_attrs2, + new_priv_attrs2_len)), &ep11_pin_blob, &ep11_pin_blob_len); RETRY_START(rc, tokdata) @@ -5979,6 +7031,12 @@ __func__, rc, spki_len, privkey_blob_len, ep11_get_ckm(tokdata, pMechanism->mechanism)); + if (check_expected_mkvp(tokdata, privkey_blob, privkey_blob_len) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + goto error; + } + if (spki_len > MAX_BLOBSIZE || privkey_blob_len > MAX_BLOBSIZE) { TRACE_ERROR("%s blobsize error\n", __func__); rc = CKR_KEY_INDIGESTIBLE; @@ -6189,12 +7247,6 @@ } error: - if (new_pPrivateKeyTemplate) - free_attribute_array(new_pPrivateKeyTemplate, - new_ulPrivateKeyAttributeCount); - if (new_pPublicKeyTemplate) - free_attribute_array(new_pPublicKeyTemplate, - new_ulPublicKeyAttributeCount); if (new_publ_attrs) free_attribute_array(new_publ_attrs, new_publ_attrs_len); if (new_priv_attrs) @@ -6206,15 +7258,10 @@ return rc; } -static CK_RV ibm_dilithium_generate_keypair(STDLL_TokData_t * tokdata, - SESSION * sess, - CK_MECHANISM_PTR pMechanism, - TEMPLATE * publ_tmpl, TEMPLATE * priv_tmpl, - CK_ATTRIBUTE_PTR pPublicKeyTemplate, - CK_ULONG ulPublicKeyAttributeCount, - CK_ATTRIBUTE_PTR pPrivateKeyTemplate, - CK_ULONG ulPrivateKeyAttributeCount, - CK_SESSION_HANDLE h) +static CK_RV ibm_pqc_generate_keypair(STDLL_TokData_t *tokdata, + SESSION *sess, + CK_MECHANISM_PTR pMechanism, + TEMPLATE *publ_tmpl, TEMPLATE *priv_tmpl) { CK_RV rc; CK_ATTRIBUTE *attr = NULL; @@ -6222,38 +7269,34 @@ size_t privkey_blob_len = sizeof(privkey_blob); unsigned char spki[MAX_BLOBSIZE]; size_t spki_len = sizeof(spki); - CK_ULONG i; - CK_ULONG bit_str_len; - CK_BYTE *key; - CK_BYTE *data, *oid, *parm; - CK_ULONG data_len, oid_len, parm_len; - CK_ULONG field_len; - CK_ATTRIBUTE_PTR new_pPublicKeyTemplate = NULL; - CK_ULONG new_ulPublicKeyAttributeCount = 0; - CK_ATTRIBUTE_PTR new_pPrivateKeyTemplate = NULL; - CK_ULONG new_ulPrivateKeyAttributeCount = 0; - CK_ULONG ktype = CKK_IBM_PQC_DILITHIUM; + CK_ULONG ktype; unsigned char *ep11_pin_blob = NULL; CK_ULONG ep11_pin_blob_len = 0; ep11_session_t *ep11_session = (ep11_session_t *) sess->private_data; - CK_BYTE *rho, *t1; CK_ATTRIBUTE *new_publ_attrs = NULL, *new_priv_attrs = NULL; CK_ULONG new_publ_attrs_len = 0, new_priv_attrs_len = 0; CK_ATTRIBUTE *new_publ_attrs2 = NULL, *new_priv_attrs2 = NULL; CK_ULONG new_publ_attrs2_len = 0, new_priv_attrs2_len = 0; - const CK_BYTE dilithium_oid[] = { 0x06, 0x0b, 0x2b, 0x06, 0x01, 0x04, 0x01, - 0x02, 0x82, 0x0b, 0x01, 0x06, 0x05 }; - - UNUSED(h); + const struct pqc_oid *pqc_oid; + const char *key_type_str; - if (pMechanism->mechanism != CKM_IBM_DILITHIUM) { + switch (pMechanism->mechanism) { + case CKM_IBM_DILITHIUM: + key_type_str = "Dilithium"; + ktype = CKK_IBM_PQC_DILITHIUM; + break; + case CKM_IBM_KYBER: + key_type_str = "Kyber"; + ktype = CKK_IBM_PQC_KYBER; + break; + default: TRACE_ERROR("Invalid mechanism provided for %s\n ", __func__); return CKR_MECHANISM_INVALID; } rc = build_ep11_attrs(tokdata, publ_tmpl, &new_publ_attrs, &new_publ_attrs_len, - ktype, CKO_PUBLIC_KEY, -1); + ktype, CKO_PUBLIC_KEY, -1, pMechanism); if (rc != CKR_OK) { TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto error; @@ -6261,15 +7304,43 @@ rc = build_ep11_attrs(tokdata, priv_tmpl, &new_priv_attrs, &new_priv_attrs_len, - ktype, CKO_PRIVATE_KEY, -1); + ktype, CKO_PRIVATE_KEY, -1, pMechanism); if (rc != CKR_OK) { TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto error; } + pqc_oid = ibm_pqc_get_keyform_mode(publ_tmpl, pMechanism->mechanism); + if (pqc_oid == NULL) + pqc_oid = ibm_pqc_get_keyform_mode(priv_tmpl, pMechanism->mechanism); + if (pqc_oid == NULL) { + switch (pMechanism->mechanism) { + case CKM_IBM_DILITHIUM: + pqc_oid = find_pqc_by_keyform(dilithium_oids, + CK_IBM_DILITHIUM_KEYFORM_ROUND2_65); + break; + case CKM_IBM_KYBER: + pqc_oid = find_pqc_by_keyform(kyber_oids, + CK_IBM_KYBER_KEYFORM_ROUND2_1024); + break; + default: + /* pqc_oid stays NULL */ + break; + } + } + if (pqc_oid == NULL) { + TRACE_ERROR("%s Failed to determine %s OID\n", __func__, key_type_str); + rc = CKR_FUNCTION_FAILED; + goto error; + } + + TRACE_INFO("%s Generate %s key with keyform %lu\n", __func__, key_type_str, + pqc_oid->keyform); + rc = add_to_attribute_array(&new_publ_attrs, &new_publ_attrs_len, - CKA_IBM_PQC_PARAMS, (CK_BYTE *)dilithium_oid, - sizeof(dilithium_oid)); + CKA_IBM_PQC_PARAMS, + (CK_BYTE *)pqc_oid->oid, + pqc_oid->oid_len); if (rc != CKR_OK) { TRACE_ERROR("%s add_to_attribute_array failed with rc=0x%lx\n", __func__, rc); @@ -6277,8 +7348,9 @@ } rc = add_to_attribute_array(&new_priv_attrs, &new_priv_attrs_len, - CKA_IBM_PQC_PARAMS,(CK_BYTE *)dilithium_oid, - sizeof(dilithium_oid)); + CKA_IBM_PQC_PARAMS, + (CK_BYTE *)pqc_oid->oid, + pqc_oid->oid_len); if (rc != CKR_OK) { TRACE_ERROR("%s add_to_attribute_array failed with rc=0x%lx\n", __func__, rc); @@ -6289,8 +7361,8 @@ new_publ_attrs, new_publ_attrs_len, &new_publ_attrs2, &new_publ_attrs2_len, -1); if (rc != CKR_OK) { - TRACE_ERROR("%s Dilithium check public key attributes failed with " - "rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s %s check public key attributes failed with " + "rc=0x%lx\n", __func__, key_type_str, rc); goto error; } @@ -6298,38 +7370,34 @@ new_priv_attrs, new_priv_attrs_len, &new_priv_attrs2, &new_priv_attrs2_len, -1); if (rc != CKR_OK) { - TRACE_ERROR("%s Dilithium check private key attributes failed with " - "rc=0x%lx\n", __func__, rc); + TRACE_ERROR("%s %s check private key attributes failed with " + "rc=0x%lx\n", __func__, key_type_str, rc); goto error; } - /* debug */ - for (i = 0; i < new_ulPrivateKeyAttributeCount; i++) { - TRACE_INFO("%s gen priv attr type=0x%lx valuelen=0x%lx attrcnt=0x%lx\n", - __func__, new_pPrivateKeyTemplate[i].type, - new_pPrivateKeyTemplate[i].ulValueLen, - new_ulPrivateKeyAttributeCount); - } - - trace_attributes(__func__, "Dilithium public key attributes:", + trace_attributes(__func__, "PQC public key attributes:", new_publ_attrs2, new_publ_attrs2_len); - trace_attributes(__func__, "Dilithium private key attributes:", + trace_attributes(__func__, "PQC private key attributes:", new_priv_attrs2, new_priv_attrs2_len); ep11_get_pin_blob(ep11_session, - (ep11_is_session_object - (pPublicKeyTemplate, ulPublicKeyAttributeCount) - || ep11_is_session_object(pPrivateKeyTemplate, - ulPrivateKeyAttributeCount)), + (ep11_is_session_object(new_publ_attrs2, + new_publ_attrs2_len) || + ep11_is_session_object(new_priv_attrs2, + new_priv_attrs2_len)), &ep11_pin_blob, &ep11_pin_blob_len); RETRY_START(rc, tokdata) - rc = dll_m_GenerateKeyPair(pMechanism, - new_publ_attrs2, new_publ_attrs2_len, - new_priv_attrs2, new_priv_attrs2_len, - ep11_pin_blob, ep11_pin_blob_len, - privkey_blob, &privkey_blob_len, spki, - &spki_len, target_info->target); + if (ep11_pqc_strength_supported(target_info, pMechanism->mechanism, + pqc_oid)) + rc = dll_m_GenerateKeyPair(pMechanism, + new_publ_attrs2, new_publ_attrs2_len, + new_priv_attrs2, new_priv_attrs2_len, + ep11_pin_blob, ep11_pin_blob_len, + privkey_blob, &privkey_blob_len, spki, + &spki_len, target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, sess) if (rc != CKR_OK) { rc = ep11_error_to_pkcs11_error(rc, sess); @@ -6344,6 +7412,12 @@ __func__, rc, spki_len, privkey_blob_len, ep11_get_ckm(tokdata, pMechanism->mechanism)); + if (check_expected_mkvp(tokdata, privkey_blob, privkey_blob_len) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + goto error; + } + if (spki_len > MAX_BLOBSIZE || privkey_blob_len > MAX_BLOBSIZE) { TRACE_ERROR("%s blobsize error\n", __func__); rc = CKR_KEY_INDIGESTIBLE; @@ -6376,115 +7450,23 @@ goto error; } - /* Decode SPKI */ - rc = ber_decode_SPKI(spki, &oid, &oid_len, &parm, &parm_len, &key, - &bit_str_len); - if (rc != CKR_OK) { - TRACE_ERROR("%s read key from SPKI failed with rc=0x%lx\n", __func__, - rc); - goto error; - } - - /* Public key must be a sequence holding two bit-strings: (rho, t1) */ - rc = ber_decode_SEQUENCE(key, &data, &data_len, &field_len); - if (rc != CKR_OK) { - TRACE_ERROR("%s read sequence failed with rc=0x%lx\n", __func__, rc); - goto error; - } - - /* Decode rho */ - rho = key + field_len - data_len; - rc = ber_decode_BIT_STRING(rho, &data, &data_len, &field_len); - if (rc != CKR_OK) { - TRACE_ERROR("%s read rho failed with rc=0x%lx\n", __func__, rc); - goto error; - } - /* Remove leading unused-bits byte, returned by ber_decode_BIT_STRING */ - data++; - data_len--; -#ifdef DEBUG - TRACE_DEBUG("%s dilithium_generate_keypair (rho):\n", __func__); - TRACE_DEBUG_DUMP(" ", data, data_len); -#endif - - /* build and add CKA_IBM_DILITHIUM_RHO for public key */ - rc = build_attribute(CKA_IBM_DILITHIUM_RHO, data, data_len, &attr); - if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); - goto error; - } - rc = template_update_attribute(publ_tmpl, attr); - if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); - goto error; - } - - /* build and add CKA_IBM_DILITHIUM_RHO for private key */ - rc = build_attribute(CKA_IBM_DILITHIUM_RHO, data, data_len, &attr); - if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); - goto error; - } - rc = template_update_attribute(priv_tmpl, attr); - if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); - goto error; - } - - /* Decode t1 */ - t1 = rho + field_len; - rc = ber_decode_BIT_STRING(t1, &data, &data_len, &field_len); - if (rc != CKR_OK) { - TRACE_ERROR("%s read t failed with rc=0x%lx\n", __func__, rc); - goto error; - } - /* Remove leading unused-bits byte, returned by ber_decode_BIT_STRING */ - data++; - data_len--; -#ifdef DEBUG - TRACE_DEBUG("%s dilithium_generate_keypair (t1):\n", __func__); - TRACE_DEBUG_DUMP(" ", data, data_len); -#endif - - /* build and add CKA_IBM_DILITHIUM_T1 for public key */ - rc = build_attribute(CKA_IBM_DILITHIUM_T1, data, data_len, &attr); - if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); - goto error; - } - rc = template_update_attribute(publ_tmpl, attr); + rc = ibm_pqc_priv_unwrap_get_data(publ_tmpl, ktype, + spki, spki_len, TRUE); if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); + TRACE_ERROR("%s ibm_pqc_priv_unwrap_get_data with rc=0x%lx\n", + __func__, rc); goto error; } - /* build and add CKA_IBM_DILITHIUM_T1 for private key */ - rc = build_attribute(CKA_IBM_DILITHIUM_T1, data, data_len, &attr); - if (rc != CKR_OK) { - TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); - goto error; - } - rc = template_update_attribute(priv_tmpl, attr); + rc = ibm_pqc_priv_unwrap_get_data(priv_tmpl, ktype, + spki, spki_len, FALSE); if (rc != CKR_OK) { - TRACE_ERROR("%s template_update_attribute failed with rc=0x%lx\n", - __func__, rc); - free(attr); + TRACE_ERROR("%s ibm_pqc_priv_unwrap_get_data with rc=0x%lx\n", + __func__, rc); goto error; } error: - if (new_pPrivateKeyTemplate) - free_attribute_array(new_pPrivateKeyTemplate, - new_ulPrivateKeyAttributeCount); - if (new_pPublicKeyTemplate) - free_attribute_array(new_pPublicKeyTemplate, - new_ulPublicKeyAttributeCount); if (new_publ_attrs) free_attribute_array(new_publ_attrs, new_publ_attrs_len); if (new_priv_attrs) @@ -6557,42 +7539,25 @@ case CKM_DH_PKCS_KEY_PAIR_GEN: rc = dh_generate_keypair(tokdata, sess, pMechanism, public_key_obj->template, - private_key_obj->template, - pPublicKeyTemplate, - ulPublicKeyAttributeCount, - pPrivateKeyTemplate, - ulPrivateKeyAttributeCount, sess->handle); + private_key_obj->template); break; case CKM_EC_KEY_PAIR_GEN: /* takes same parameters as RSA */ case CKM_RSA_PKCS_KEY_PAIR_GEN: case CKM_RSA_X9_31_KEY_PAIR_GEN: rc = rsa_ec_generate_keypair(tokdata, sess, pMechanism, public_key_obj->template, - private_key_obj->template, - pPublicKeyTemplate, - ulPublicKeyAttributeCount, - pPrivateKeyTemplate, - ulPrivateKeyAttributeCount, sess->handle); + private_key_obj->template); break; - case CKM_DSA_PARAMETER_GEN: case CKM_DSA_KEY_PAIR_GEN: rc = dsa_generate_keypair(tokdata, sess, pMechanism, public_key_obj->template, - private_key_obj->template, - pPublicKeyTemplate, - ulPublicKeyAttributeCount, - pPrivateKeyTemplate, - ulPrivateKeyAttributeCount, sess->handle); + private_key_obj->template); break; case CKM_IBM_DILITHIUM: - rc = ibm_dilithium_generate_keypair(tokdata, sess, pMechanism, - public_key_obj->template, - private_key_obj->template, - pPublicKeyTemplate, - ulPublicKeyAttributeCount, - pPrivateKeyTemplate, - ulPrivateKeyAttributeCount, - sess->handle); + case CKM_IBM_KYBER: + rc = ibm_pqc_generate_keypair(tokdata, sess, pMechanism, + public_key_obj->template, + private_key_obj->template); break; default: TRACE_ERROR("%s invalid mech %s\n", __func__, @@ -6616,7 +7581,7 @@ (void *)public_key_obj, (void *)private_key_obj); } - rc = update_ep11_attrs_from_blob(tokdata, private_key_obj->template); + rc = update_ep11_attrs_from_blob(tokdata, sess, private_key_obj->template, FALSE); if (rc != CKR_OK) { TRACE_ERROR("%s update_ep11_attrs_from_blob failed with rc=0x%lx\n", __func__, rc); @@ -6849,7 +7814,6 @@ CK_BBOOL sign) { OBJECT *key_obj = NULL; - CK_BYTE *ptr = NULL; CK_KEY_TYPE keytype; CK_OBJECT_CLASS class; CK_BBOOL flag; @@ -6947,9 +7911,9 @@ ctx->context_len = 0; ctx->context = NULL; ctx->key = key; - ctx->mech.ulParameterLen = mech->ulParameterLen; ctx->mech.mechanism = mech->mechanism; - ctx->mech.pParameter = ptr; + ctx->mech.pParameter = NULL; + ctx->mech.ulParameterLen = 0; ctx->multi_init = FALSE; ctx->multi = FALSE; ctx->active = TRUE; @@ -6965,6 +7929,138 @@ return rc; } +CK_RV ep11tok_check_single_mech_key(STDLL_TokData_t *tokdata, SESSION * session, + CK_MECHANISM *mech, CK_OBJECT_HANDLE key, + CK_ULONG operation) +{ + OBJECT *key_obj = NULL; + size_t blob_len = 0; + CK_BYTE *blob; + CK_ATTRIBUTE_TYPE type; + CK_BBOOL flag; + int policy_op; + const char *str_op; + CK_RV rc; + + switch (operation) { + case OP_ENCRYPT_INIT: + policy_op = POLICY_CHECK_ENCRYPT; + type = CKA_ENCRYPT; + str_op = "encrypt"; + break; + case OP_DECRYPT_INIT: + policy_op = POLICY_CHECK_DECRYPT; + type = CKA_DECRYPT; + str_op = "decrypt"; + break; + case OP_SIGN_INIT: + policy_op = POLICY_CHECK_SIGNATURE; + type = CKA_SIGN; + str_op = "sign"; + break; + case OP_VERIFY_INIT: + policy_op = POLICY_CHECK_VERIFY; + type = CKA_VERIFY; + str_op = "verify"; + break; + default: + TRACE_ERROR("%s\n", ock_err(ERR_ARGUMENTS_BAD)); + return CKR_ARGUMENTS_BAD; + } + + rc = h_opaque_2_blob(tokdata, key, &blob, &blob_len, &key_obj, READ_LOCK); + if (rc != CKR_OK) { + TRACE_ERROR("%s no blob rc=0x%lx\n", __func__, rc); + goto error; + } + + rc = template_attribute_get_bool(key_obj->template, type, &flag); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find attribute 0x%lx for the key (op: %s).\n", + type, str_op); + rc = CKR_KEY_FUNCTION_NOT_PERMITTED; + goto error; + } + + if (flag != TRUE) { + TRACE_ERROR("%s\n", ock_err(ERR_KEY_FUNCTION_NOT_PERMITTED)); + rc = CKR_KEY_FUNCTION_NOT_PERMITTED; + goto error; + } + + if (!key_object_is_mechanism_allowed(key_obj->template, mech->mechanism)) { + TRACE_ERROR("Mechanism not allowed per CKA_ALLOWED_MECHANISMS.\n"); + rc = CKR_MECHANISM_INVALID; + goto error; + } + + rc = tokdata->policy->is_mech_allowed(tokdata->policy, mech, + &key_obj->strength, policy_op, + session); + if (rc != CKR_OK) { + TRACE_ERROR("POLICY_VIOLATION on %s initialization\n", str_op); + goto error; + } + +error: + object_put(tokdata, key_obj, TRUE); + key_obj = NULL; + + return rc; +} + +struct ECDSA_OTHER_MECH_PARAM { + CK_MECHANISM mech; + ECSG_Var_t param; +}; + +static CK_RV ep11tok_ecdsa_other_mech_adjust(CK_MECHANISM *mech, + struct ECDSA_OTHER_MECH_PARAM *mech_ep11) +{ + CK_IBM_ECDSA_OTHER_PARAMS *param; + + if (mech->mechanism != CKM_IBM_ECDSA_OTHER) + return CKR_MECHANISM_INVALID; + + if (mech->ulParameterLen != sizeof(CK_IBM_ECDSA_OTHER_PARAMS) || + mech->pParameter == NULL) { + TRACE_ERROR("%s Invalid mechanism param for CKM_IBM_ECDSA_OTHER\n", + __func__); + return CKR_MECHANISM_PARAM_INVALID; + } + + mech_ep11->mech.mechanism = CKM_IBM_ECDSA_OTHER; + mech_ep11->mech.pParameter = &mech_ep11->param; + mech_ep11->mech.ulParameterLen = sizeof(mech_ep11->param); + + param = (CK_IBM_ECDSA_OTHER_PARAMS *)mech->pParameter; + switch (param->submechanism) { + case CKM_IBM_ECSDSA_RAND: + mech_ep11->param = ECSG_IBM_ECSDSA_S256; + break; + case CKM_IBM_ECSDSA_COMPR_MULTI: + mech_ep11->param = ECSG_IBM_ECSDSA_COMPR_MULTI; + break; + default: + TRACE_ERROR("%s Invalid sub mechanism for CKM_IBM_ECDSA_OTHER: %lu\n", + __func__, param->submechanism); + return CKR_MECHANISM_PARAM_INVALID; + } + + return CKR_OK; +} + +CK_BOOL ep11tok_mech_single_only(CK_MECHANISM *mech) +{ + switch (mech->mechanism) { + case CKM_IBM_ECDSA_OTHER: + case CKM_IBM_KYBER: + return CK_TRUE; + default: + return CK_FALSE; + } +} + CK_RV ep11tok_sign_init(STDLL_TokData_t * tokdata, SESSION * session, CK_MECHANISM * mech, CK_BBOOL recover_mode, CK_OBJECT_HANDLE key) @@ -6976,6 +8072,7 @@ SIGN_VERIFY_CONTEXT *ctx = &session->sign_ctx; size_t ep11_sign_state_l = MAX_SIGN_STATE_BYTES; CK_BYTE *ep11_sign_state = malloc(ep11_sign_state_l); + struct ECDSA_OTHER_MECH_PARAM mech_ep11; UNUSED(recover_mode); @@ -6997,6 +8094,7 @@ session); if (rc != CKR_OK) { TRACE_ERROR("POLICY VIOLATION: Sign init\n"); + free(ep11_sign_state); goto done; } @@ -7044,9 +8142,23 @@ goto done; } + if (mech->mechanism == CKM_IBM_ECDSA_OTHER) { + rc = ep11tok_ecdsa_other_mech_adjust(mech, &mech_ep11); + if (rc != CKR_OK) { + free(ep11_sign_state); + goto done; + } + mech = &mech_ep11.mech; + } + RETRY_START(rc, tokdata) - rc = dll_m_SignInit(ep11_sign_state, &ep11_sign_state_l, - mech, keyblob, keyblobsize, target_info->target); + if (ep11_pqc_obj_strength_supported(target_info, mech->mechanism, + key_obj)) + rc = dll_m_SignInit(ep11_sign_state, &ep11_sign_state_l, + mech, keyblob, keyblobsize, + target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { @@ -7063,6 +8175,21 @@ ctx->context = ep11_sign_state; ctx->context_len = ep11_sign_state_l; ctx->pkey_active = FALSE; + if (mech != &ctx->mech) { /* deferred init dup'ed mech already */ + ctx->mech.mechanism = mech->mechanism; + if (mech->ulParameterLen > 0 && mech->pParameter != NULL) { + ctx->mech.pParameter = (CK_BYTE *) malloc(mech->ulParameterLen); + if (ctx->mech.pParameter == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + sign_mgr_cleanup(tokdata, session, ctx); + goto done; + } + memcpy(ctx->mech.pParameter, mech->pParameter, + mech->ulParameterLen); + ctx->mech.ulParameterLen = mech->ulParameterLen; + } + } TRACE_INFO("%s rc=0x%lx blobsize=0x%zx key=0x%lx mech=0x%lx\n", __func__, rc, keyblobsize, key, mech->mechanism); @@ -7233,6 +8360,7 @@ size_t keyblobsize = 0; CK_BYTE *keyblob; OBJECT *key_obj = NULL; + struct ECDSA_OTHER_MECH_PARAM mech_ep11; rc = h_opaque_2_blob(tokdata, key, &keyblob, &keyblobsize, &key_obj, READ_LOCK); @@ -7255,9 +8383,20 @@ goto done; } + if (mech->mechanism == CKM_IBM_ECDSA_OTHER) { + rc = ep11tok_ecdsa_other_mech_adjust(mech, &mech_ep11); + if (rc != CKR_OK) + goto done; + mech = &mech_ep11.mech; + } + RETRY_START(rc, tokdata) - rc = dll_m_SignSingle(keyblob, keyblobsize, mech, in_data, in_data_len, - signature, sig_len, target_info->target); + if (ep11_pqc_obj_strength_supported(target_info, mech->mechanism, + key_obj)) + rc = dll_m_SignSingle(keyblob, keyblobsize, mech, in_data, in_data_len, + signature, sig_len, target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { rc = ep11_error_to_pkcs11_error(rc, session); @@ -7288,6 +8427,7 @@ SIGN_VERIFY_CONTEXT *ctx = &session->verify_ctx; size_t ep11_sign_state_l = MAX_SIGN_STATE_BYTES; CK_BYTE *ep11_sign_state = malloc(ep11_sign_state_l); + struct ECDSA_OTHER_MECH_PARAM mech_ep11; if (!ep11_sign_state) { TRACE_ERROR("%s Memory allocation failed\n", __func__); @@ -7306,6 +8446,7 @@ session); if (rc != CKR_OK) { TRACE_ERROR("POLICY VIOLATION: Verify init\n"); + free(ep11_sign_state); goto done; } @@ -7366,9 +8507,22 @@ goto done; } + if (mech->mechanism == CKM_IBM_ECDSA_OTHER) { + rc = ep11tok_ecdsa_other_mech_adjust(mech, &mech_ep11); + if (rc != CKR_OK) { + free(ep11_sign_state); + goto done; + } + mech = &mech_ep11.mech; + } + RETRY_START(rc, tokdata) - rc = dll_m_VerifyInit(ep11_sign_state, &ep11_sign_state_l, mech, - spki, spki_len, target_info->target); + if (ep11_pqc_obj_strength_supported(target_info, mech->mechanism, + key_obj)) + rc = dll_m_VerifyInit(ep11_sign_state, &ep11_sign_state_l, mech, + spki, spki_len, target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { @@ -7383,6 +8537,21 @@ ctx->context = ep11_sign_state; ctx->context_len = ep11_sign_state_l; ctx->pkey_active = FALSE; + if (mech != &ctx->mech) { /* deferred init dup'ed mech already */ + ctx->mech.mechanism = mech->mechanism; + if (mech->ulParameterLen > 0 && mech->pParameter != NULL) { + ctx->mech.pParameter = (CK_BYTE *) malloc(mech->ulParameterLen); + if (ctx->mech.pParameter == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + verify_mgr_cleanup(tokdata, session, ctx); + goto done; + } + memcpy(ctx->mech.pParameter, mech->pParameter, + mech->ulParameterLen); + ctx->mech.ulParameterLen = mech->ulParameterLen; + } + } TRACE_INFO("%s rc=0x%lx spki_len=0x%zx key=0x%lx " "ep11_sign_state_l=0x%zx mech=0x%lx\n", __func__, @@ -7552,6 +8721,7 @@ CK_BYTE *spki; size_t spki_len = 0; OBJECT *key_obj = NULL; + struct ECDSA_OTHER_MECH_PARAM mech_ep11; rc = h_opaque_2_blob(tokdata, key, &spki, &spki_len, &key_obj, READ_LOCK); if (rc != CKR_OK) { @@ -7583,9 +8753,20 @@ goto done; } + if (mech->mechanism == CKM_IBM_ECDSA_OTHER) { + rc = ep11tok_ecdsa_other_mech_adjust(mech, &mech_ep11); + if (rc != CKR_OK) + goto done; + mech = &mech_ep11.mech; + } + RETRY_START(rc, tokdata) - rc = dll_m_VerifySingle(spki, spki_len, mech, in_data, in_data_len, - signature, sig_len, target_info->target); + if (ep11_pqc_obj_strength_supported(target_info, mech->mechanism, + key_obj)) + rc = dll_m_VerifySingle(spki, spki_len, mech, in_data, in_data_len, + signature, sig_len, target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { rc = ep11_error_to_pkcs11_error(rc, session); @@ -7782,9 +8963,14 @@ } RETRY_START(rc, tokdata) - rc = dll_m_DecryptSingle(keyblob, keyblobsize, mech, input_data, - input_data_len, output_data, p_output_data_len, - target_info->target); + if (ep11_pqc_obj_strength_supported(target_info, mech->mechanism, + key_obj)) + rc = dll_m_DecryptSingle(keyblob, keyblobsize, mech, input_data, + input_data_len, output_data, + p_output_data_len, + target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { rc = ep11_error_to_pkcs11_error(rc, session); @@ -7992,9 +9178,14 @@ } RETRY_START(rc, tokdata) - rc = dll_m_EncryptSingle(keyblob, keyblobsize, mech, input_data, - input_data_len, output_data, p_output_data_len, - target_info->target); + if (ep11_pqc_obj_strength_supported(target_info, mech->mechanism, + key_obj)) + rc = dll_m_EncryptSingle(keyblob, keyblobsize, mech, input_data, + input_data_len, output_data, + p_output_data_len, + target_info->target); + else + rc = CKR_KEY_SIZE_RANGE; RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { rc = ep11_error_to_pkcs11_error(rc, session); @@ -8080,7 +9271,13 @@ free(ep11_state); goto done; case CKR_FUNCTION_NOT_SUPPORTED: - /* fallback into ep11 path */ + /* if mechanism is AES XTS, return error else fallback to ep11 path */ + if (mech->mechanism == CKM_AES_XTS) { + TRACE_ERROR("EP11 AES XTS mech is supported only for protected keys"); + rc = CKR_KEY_UNEXTRACTABLE; + free(ep11_state); + goto done; + } break; default: /* internal error or lock problem */ @@ -8099,6 +9296,21 @@ ctx->context = ep11_state; ctx->context_len = ep11_state_l; ctx->pkey_active = FALSE; + if (mech != &ctx->mech) { /* deferred init dup'ed mech already */ + ctx->mech.mechanism = mech->mechanism; + if (mech->ulParameterLen > 0 && mech->pParameter != NULL) { + ctx->mech.pParameter = (CK_BYTE *) malloc(mech->ulParameterLen); + if (ctx->mech.pParameter == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + decr_mgr_cleanup(tokdata, session, ctx); + goto done; + } + memcpy(ctx->mech.pParameter, mech->pParameter, + mech->ulParameterLen); + ctx->mech.ulParameterLen = mech->ulParameterLen; + } + } if (rc != CKR_OK) { decr_mgr_cleanup(tokdata, session, ctx); rc = ep11_error_to_pkcs11_error(rc, session); @@ -8132,6 +9344,21 @@ ctx->context = ep11_state; ctx->context_len = ep11_state_l; ctx->pkey_active = FALSE; + if (mech != &ctx->mech) { /* deferred init dup'ed mech already */ + ctx->mech.mechanism = mech->mechanism; + if (mech->ulParameterLen > 0 && mech->pParameter != NULL) { + ctx->mech.pParameter = (CK_BYTE *) malloc(mech->ulParameterLen); + if (ctx->mech.pParameter == NULL) { + TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); + rc = CKR_HOST_MEMORY; + encr_mgr_cleanup(tokdata, session, ctx); + goto done; + } + memcpy(ctx->mech.pParameter, mech->pParameter, + mech->ulParameterLen); + ctx->mech.ulParameterLen = mech->ulParameterLen; + } + } if (rc != CKR_OK) { encr_mgr_cleanup(tokdata, session, ctx); rc = ep11_error_to_pkcs11_error(rc, session); @@ -8216,6 +9443,7 @@ OBJECT *key_obj = NULL, *wrap_key_obj = NULL, *sobj = NULL; CK_BYTE *sign_blob = NULL; size_t sign_blob_len = ~0; + CK_KEY_TYPE ktype; /* ep11 weakness: * it does not set *p_wrapped_key_len if wrapped_key == NULL @@ -8242,12 +9470,22 @@ return rc; } + rc = template_attribute_get_ulong(wrap_key_obj->template, CKA_KEY_TYPE, &ktype); + if (rc != CKR_OK) { + TRACE_ERROR("Invalid key type attribute\n"); + goto done; + } + + if (mech->mechanism == CKM_AES_XTS || ktype == CKK_AES_XTS) { + TRACE_ERROR("%s Key wrap with AES-XTS is not supported\n", __func__); + rc = CKR_KEY_TYPE_INCONSISTENT; + goto done; + } + if (!key_object_is_mechanism_allowed(wrap_key_obj->template, mech->mechanism)) { TRACE_ERROR("Mechanism not allowed per CKA_ALLOWED_MECHANISMS.\n"); rc = CKR_MECHANISM_INVALID; - if (size_query) - free(wrapped_key); goto done; } @@ -8257,8 +9495,17 @@ if (rc != CKR_OK) { TRACE_ERROR("%s h_opaque_2_blob(key) failed with rc=0x%lx\n", __func__, rc); - if (size_query) - free(wrapped_key); + goto done; + } + rc = template_attribute_get_ulong(key_obj->template, CKA_KEY_TYPE, &ktype); + if (rc != CKR_OK) { + TRACE_ERROR("Invalid key type attribute\n"); + goto done; + } + + if (ktype == CKK_AES_XTS) { + TRACE_ERROR("%s Wrapping an AES-XTS key is not supported\n", __func__); + rc = CKR_KEY_TYPE_INCONSISTENT; goto done; } rc = tokdata->policy->is_mech_allowed(tokdata->policy, mech, @@ -8278,8 +9525,6 @@ key_obj->template)) { TRACE_ERROR("Wrap template does not match.\n"); rc = CKR_KEY_HANDLE_INVALID; - if (size_query) - free(wrapped_key); goto done; } @@ -8331,14 +9576,14 @@ __func__, rc, (void *)wrapped_key, *p_wrapped_key_len); } - if (size_query) - free(wrapped_key); - done: if (rc == CKR_OK && !size_query) INC_COUNTER(tokdata, session, mech, wrap_key_obj, POLICY_STRENGTH_IDX_0); + if (size_query) + free(wrapped_key); + object_put(tokdata, wrap_key_obj, TRUE); wrap_key_obj = NULL; object_put(tokdata, key_obj, TRUE); @@ -8382,6 +9627,7 @@ CK_BYTE *verifyblob = NULL; size_t verifyblobsize = ~0; OBJECT *vobj = NULL; + CK_KEY_TYPE keytype; /* get wrapping key blob */ rc = h_opaque_2_blob(tokdata, wrapping_key, &wrapping_blob, @@ -8391,6 +9637,19 @@ __func__, rc); return rc; } + + rc = template_attribute_get_ulong(kobj->template, CKA_KEY_TYPE, &keytype); + if (rc != CKR_OK) { + TRACE_ERROR("Invalid key type attribute\n"); + goto done; + } + + if (mech->mechanism == CKM_AES_XTS || keytype == CKK_AES_XTS) { + TRACE_ERROR("%s Key unwrap with AES-XTS is not supported\n", __func__); + rc = CKR_KEY_TYPE_INCONSISTENT; + goto done; + } + rc = tokdata->policy->is_mech_allowed(tokdata->policy, mech, &kobj->strength, POLICY_CHECK_UNWRAP, session); @@ -8502,6 +9761,12 @@ goto error; } + if (ktype == CKK_AES_XTS) { + TRACE_ERROR("%s Unwrapping an AES-XTS key is not supported\n", __func__); + rc = CKR_KEY_TYPE_INCONSISTENT; + goto done; + } + /* Start creating the key object */ rc = object_mgr_create_skel(tokdata, session, new_attrs, new_attrs_len, MODE_UNWRAP, class, ktype, &key_obj); @@ -8511,7 +9776,10 @@ goto error; } - rc = build_ep11_attrs(tokdata, key_obj->template, &new_attrs2, &new_attrs2_len, ktype, *(CK_OBJECT_CLASS *) cla_attr->pValue, -1); + rc = build_ep11_attrs(tokdata, key_obj->template, + &new_attrs2, &new_attrs2_len, + ktype, *(CK_OBJECT_CLASS *) cla_attr->pValue, -1, + mech); if (rc != CKR_OK) { TRACE_ERROR("%s build_ep11_attrs failed with rc=0x%lx\n", __func__, rc); goto error; @@ -8543,6 +9811,12 @@ TRACE_INFO("%s m_UnwrapKey rc=0x%lx blobsize=0x%zx mech=0x%lx\n", __func__, rc, keyblobsize, mech->mechanism); + if (check_expected_mkvp(tokdata, keyblob, keyblobsize) != CKR_OK) { + TRACE_ERROR("%s\n", ock_err(ERR_DEVICE_ERROR)); + rc = CKR_DEVICE_ERROR; + goto error; + } + rc = build_attribute(CKA_IBM_OPAQUE, keyblob, keyblobsize, &attr); if (rc != CKR_OK) { TRACE_ERROR("%s build_attribute failed with rc=0x%lx\n", __func__, rc); @@ -8558,7 +9832,8 @@ attr = NULL; if (isab) { - rc = ab_unwrap_update_template(tokdata, keyblob, keyblobsize, key_obj, + rc = ab_unwrap_update_template(tokdata, session, + keyblob, keyblobsize, key_obj, *(CK_KEY_TYPE *) keytype_attr->pValue); if (rc != CKR_OK) { TRACE_ERROR("ab_unwrap_update_template failed with rc=0x%08lx\n", rc); @@ -8566,7 +9841,7 @@ } } - rc = update_ep11_attrs_from_blob(tokdata, key_obj->template); + rc = update_ep11_attrs_from_blob(tokdata, session, key_obj->template, FALSE); if (rc != CKR_OK) { TRACE_ERROR("%s update_ep11_attrs_from_blob failed with rc=0x%lx\n", __func__, rc); @@ -8644,7 +9919,12 @@ rc = dh_priv_unwrap_get_data(key_obj->template, csum, cslen); break; case CKK_IBM_PQC_DILITHIUM: - rc = ibm_dilithium_priv_unwrap_get_data(key_obj->template, csum, cslen); + rc = ibm_dilithium_priv_unwrap_get_data(key_obj->template, + csum, cslen, FALSE); + break; + case CKK_IBM_PQC_KYBER: + rc = ibm_kyber_priv_unwrap_get_data(key_obj->template, + csum, cslen, FALSE); break; } @@ -8715,7 +9995,9 @@ CKM_AES_CBC_PAD, CKM_AES_CMAC, CKM_AES_ECB, + CKM_AES_XTS, CKM_AES_KEY_GEN, + CKM_AES_XTS_KEY_GEN, CKM_DES2_KEY_GEN, CKM_DES3_CBC, CKM_DES3_CBC_PAD, @@ -8724,10 +10006,8 @@ CKM_DES3_KEY_GEN, CKM_DH_PKCS_DERIVE, CKM_DH_PKCS_KEY_PAIR_GEN, - CKM_DH_PKCS_PARAMETER_GEN, CKM_DSA, CKM_DSA_KEY_PAIR_GEN, - CKM_DSA_PARAMETER_GEN, CKM_DSA_SHA1, CKM_EC_KEY_PAIR_GEN, CKM_ECDH1_DERIVE, @@ -8743,6 +10023,7 @@ CKM_IBM_EC_X448, CKM_IBM_ED25519_SHA512, CKM_IBM_ED448_SHA3, + CKM_IBM_KYBER, CKM_IBM_SHA3_224, CKM_IBM_SHA3_224_HMAC, CKM_IBM_SHA3_256, @@ -8791,6 +10072,8 @@ CKM_SHA_1_HMAC, CKM_GENERIC_SECRET_KEY_GEN, CKM_IBM_ATTRIBUTEBOUND_WRAP, + CKM_IBM_ECDSA_OTHER, + CKM_IBM_BTC_DERIVE, }; static const CK_ULONG supported_mech_list_len = @@ -8875,6 +10158,8 @@ if (rc != CKR_BUFFER_TOO_SMALL) goto out; } + /* counter was updated in case of CKR_BUFFER_TOO_SMALL */ + *pulCount = counter; } while (rc == CKR_BUFFER_TOO_SMALL); for (i = 0; i < counter; i++) { @@ -8892,6 +10177,11 @@ *pulCount -= 1; } } + + if (ep11tok_is_mechanism_supported(tokdata, CKM_AES_XTS) == CKR_OK && + ep11tok_is_mechanism_supported(tokdata, CKM_AES_XTS_KEY_GEN) == CKR_OK) { + *pulCount += 2; + } } else { /* 2. call, content request */ size = *pulCount; @@ -8958,6 +10248,16 @@ *pulCount = *pulCount + 1; } } + + if (ep11tok_is_mechanism_supported(tokdata, CKM_AES_XTS) == CKR_OK && + ep11tok_is_mechanism_supported(tokdata, CKM_AES_XTS_KEY_GEN) == CKR_OK) { + if (*pulCount < size) + pMechanismList[*pulCount] = CKM_AES_XTS_KEY_GEN; + *pulCount = *pulCount + 1; + if (*pulCount < size) + pMechanismList[*pulCount] = CKM_AES_XTS; + *pulCount = *pulCount + 1; + } if (*pulCount > size) rc = CKR_BUFFER_TOO_SMALL; } @@ -8976,6 +10276,8 @@ ep11_private_data_t *ep11_data = tokdata->private_data; CK_VERSION ver1_3 = { .major = 1, .minor = 3 }; CK_VERSION ver3 = { .major = 3, .minor = 0 }; + CK_VERSION ver3_1 = { .major = 3, .minor = 0x10 }; + CK_VERSION ver4 = { .major = 4, .minor = 0 }; CK_BBOOL found = FALSE; CK_ULONG i; int status; @@ -9128,6 +10430,23 @@ } break; + case CKM_IBM_KYBER: + if (compare_ck_version(&ep11_data->ep11_lib_version, &ver4) < 0) { + TRACE_INFO("%s Mech '%s' banned due to host library version\n", + __func__, ep11_get_ckm(tokdata, type)); + rc = CKR_MECHANISM_INVALID; + goto out; + } + status = check_required_versions(tokdata, ibm_kyber_req_versions, + NUM_KYBER_REQ); + if (status != 1) { + TRACE_INFO("%s Mech '%s' banned due to mixed firmware versions\n", + __func__, ep11_get_ckm(tokdata, type)); + rc = CKR_MECHANISM_INVALID; + goto out; + } + break; + case CKM_IBM_CPACF_WRAP: if (compare_ck_version(&ep11_data->ep11_lib_version, &ver3) <= 0) { TRACE_INFO("%s Mech '%s' banned due to host library version\n", @@ -9145,6 +10464,52 @@ goto out; } break; + + case CKM_IBM_BTC_DERIVE: + if (compare_ck_version(&ep11_data->ep11_lib_version, &ver3_1) < 0) { + TRACE_INFO("%s Mech '%s' banned due to host library version\n", + __func__, ep11_get_ckm(tokdata, type)); + rc = CKR_MECHANISM_INVALID; + goto out; + } + status = check_required_versions(tokdata, ibm_btc_req_versions, + NUM_BTC_REQ); + if (status != 1) { + TRACE_INFO("%s Mech '%s' banned due to mixed firmware versions\n", + __func__, ep11_get_ckm(tokdata, type)); + rc = CKR_MECHANISM_INVALID; + goto out; + } + break; + + case CKM_IBM_ECDSA_OTHER: + if (compare_ck_version(&ep11_data->ep11_lib_version, &ver3_1) < 0) { + TRACE_INFO("%s Mech '%s' banned due to host library version\n", + __func__, ep11_get_ckm(tokdata, type)); + rc = CKR_MECHANISM_INVALID; + goto out; + } + status = check_required_versions(tokdata, ibm_ecdsa_other_req_versions, + NUM_ECDSA_OTHER_REQ); + if (status != 1) { + TRACE_INFO("%s Mech '%s' banned due to mixed firmware versions\n", + __func__, ep11_get_ckm(tokdata, type)); + rc = CKR_MECHANISM_INVALID; + goto out; + } + break; + + case CKM_AES_XTS: + case CKM_AES_XTS_KEY_GEN: + if (ep11tok_pkey_option_disabled(tokdata) || ep11_data->msa_level < 4 || + ep11tok_is_mechanism_supported(tokdata, CKM_IBM_CPACF_WRAP) != CKR_OK || + ep11tok_is_mechanism_supported(tokdata, CKM_AES_KEY_GEN) != CKR_OK) { + TRACE_INFO("%s Mech '%s' not suppported\n", __func__, + ep11_get_ckm(tokdata, type)); + rc = CKR_MECHANISM_INVALID; + goto out; + } + break; } out: @@ -9209,7 +10574,21 @@ if (target_info == NULL) return CKR_FUNCTION_FAILED; - rc = dll_m_GetMechanismInfo(0, type, pInfo, target_info->target); + switch (type) { + case CKM_AES_XTS: + pInfo->ulMinKeySize = 32; + pInfo->ulMaxKeySize = 64; + pInfo->flags = (CK_FLAGS)(CKF_ENCRYPT|CKF_DECRYPT); + break; + case CKM_AES_XTS_KEY_GEN: + pInfo->ulMinKeySize = 32; + pInfo->ulMaxKeySize = 64; + pInfo->flags = (CK_FLAGS)(CKF_HW|CKF_GENERATE); + break; + default: + rc = dll_m_GetMechanismInfo(0, type, pInfo, target_info->target); + break; + } put_target_info(tokdata, target_info); @@ -9305,59 +10684,248 @@ return tokdata->policy->update_mech_info(tokdata->policy, type, pInfo); } +static CK_RV ep11_config_add_apqn(ep11_private_data_t *ep11_data, + struct ConfigNumPairNode *pair, + const char *fname) +{ + if (pair->value1 > 255) { + OCK_SYSLOG(LOG_ERR, "%s: Error: Expected valid adapter" + " number, found '%lu' in config file '%s' at line %d\n", + __func__, pair->value1, fname, pair->base.line); + TRACE_ERROR(" Error: Expected valid adapter number, found '%lu' in " + "config file '%s' at line %d\n", pair->value1, fname, + pair->base.line); + return CKR_ARGUMENTS_BAD; + } -/* used for reading in the adapter config file, - * converts a 'token' to a number, returns 0 with success - */ -static inline short check_n(ep11_target_t * target, char *nptr, int *apqn_i) + if (pair->value2 > 255) { + OCK_SYSLOG(LOG_ERR, "%s: Error: Expected valid domain" + " number, found '%lu' in config file '%s' at line %d\n", + __func__, pair->value2, fname, pair->base.line); + TRACE_ERROR(" Error: Expected valid domain number, found '%lu' in " + "config file '%s' at line %d\n", pair->value2, fname, + pair->base.line); + return CKR_ARGUMENTS_BAD; + } + + if (ep11_data->target_list.length >= MAX_APQN) { + OCK_SYSLOG(LOG_ERR,"%s: Error: Too many APQNs in config " + "file '%s' (max %d)\n", __func__, fname, (int) MAX_APQN); + TRACE_ERROR("Too many APQNs in config file '%s' (max %d)\n", + fname, (int) MAX_APQN); + return CKR_BUFFER_TOO_SMALL; + } + + ep11_data->target_list.apqns[ep11_data->target_list.length * 2] = + pair->value1; + ep11_data->target_list.apqns[ep11_data->target_list.length * 2 + 1] = + pair->value2; + ep11_data->target_list.length++; + + return CKR_OK; +} + +static void ep11_config_parse_error(int line, int col, const char *msg) { - int num; + OCK_SYSLOG(LOG_ERR, "Error parsing EP11 config file: line %d column %d: %s\n", + line, col, msg); + TRACE_ERROR("Error parsing EP11 config file: line %d column %d: %s\n", + line, col, msg); +} - if (sscanf(nptr, "%i", &num) != 1) { - TRACE_ERROR("%s invalid number '%s'\n", __func__, nptr); - return -1; +static void ep11_config_error_token(const char *fname, const char *key, + int line, const char *expected) +{ + if (expected != NULL) { + OCK_SYSLOG(LOG_ERR, "Error parsing config file '%s': unexpected token " + "'%s' at line %d, expected %s\n", fname, + key != NULL ? key : "(none)", line, expected); + TRACE_ERROR("Error parsing config file '%s': unexpected token " + " '%s' at line %d, expected %s\n", fname, + key != NULL ? key : "(none)", line, expected); + + } else { + OCK_SYSLOG(LOG_ERR, "Error parsing config file '%s': " + "unexpected token '%s' at line %d\n", fname, + key != NULL ? key : "(none)", line); + TRACE_ERROR("Error parsing config file '%s': unexpected token " + "'%s' at line %d\n", fname, key != NULL ? key : "(none)", line); } +} + +static void ep11_config_error_eof(const char *fname, const char *expected) +{ + if (expected != NULL) { + OCK_SYSLOG(LOG_ERR, "Error: Unexpected end of file found in config " + "file '%s', expected %s\n", fname, expected); + TRACE_ERROR("Error: Unexpected end of file found in config file '%s', " + "expected %s\\n", fname, expected); - if (num < 0 || num > 255) { - TRACE_ERROR("%s invalid number '%s' %d\n", __func__, nptr, num); - return -1; - } else if (*apqn_i < 0 || *apqn_i >= MAX_APQN * 2) { - TRACE_ERROR("%s invalid amount of numbers %d\n", __func__, num); - return -1; } else { - /* insert number into target variable */ - target->apqns[*apqn_i] = (short) num; - /* how many APQNs numbers so far */ - *apqn_i = *apqn_i + 1; - return 0; + OCK_SYSLOG(LOG_ERR, "Error: Unexpected end of file found in config " + "file '%s'\n", fname); + TRACE_ERROR("Error: Unexpected end of file found in config file '%s'\n", + fname); + } +} + +static CK_RV ep11_config_next(struct ConfigBaseNode **c, unsigned typemask, + const char *fname, const char *expected) +{ + *c = (*c)->next; + + if (*c == NULL) { + ep11_config_error_eof(fname, expected); + return CKR_FUNCTION_FAILED; + } + + if (!confignode_hastype(*c, typemask)) { + ep11_config_error_token(fname, (*c)->key, (*c)->line, expected); + return CKR_FUNCTION_FAILED; + } + + return CKR_OK; +} + +static CK_RV ep11_config_set_cpfilter(ep11_private_data_t *ep11_data, + const char *fname, const char *strval) +{ + if (strlen(strval) > + sizeof(ep11_data->cp_filter_config_filename) - 1) { + TRACE_ERROR("%s CP-Filter config file name is too long: '%s'\n", + __func__, strval); + OCK_SYSLOG(LOG_ERR, + "%s: Error: CP-Filter config file name '%s' is " + "too long in config file '%s'\n", __func__, strval, fname); + return CKR_FUNCTION_FAILED; + } + + strncpy(ep11_data->cp_filter_config_filename, strval, + sizeof(ep11_data->cp_filter_config_filename) - 1); + ep11_data->cp_filter_config_filename[ + sizeof(ep11_data->cp_filter_config_filename) - 1] = '\0'; + + return CKR_OK; +} + +static CK_RV ep11_config_set_pkey_mode(ep11_private_data_t *ep11_data, + const char *fname, const char *strval) +{ + if (strcmp(strval, "DISABLED") == 0) + ep11_data->pkey_mode = PKEY_MODE_DISABLED; + else if (strcmp(strval, "DEFAULT") == 0) + ep11_data->pkey_mode = PKEY_MODE_DEFAULT; + else if (strcmp(strval, "ENABLE4NONEXTR") == 0) + ep11_data->pkey_mode = PKEY_MODE_ENABLE4NONEXTR; + else { + TRACE_ERROR("%s unsupported PKEY mode : '%s'\n", __func__, strval); + OCK_SYSLOG(LOG_ERR,"%s: Error: unsupported PKEY mode '%s' " + "in config file '%s'\n", __func__, strval, fname); + return CKR_FUNCTION_FAILED; + } + + return CKR_OK; +} + +static CK_RV ep11_config_set_libica(ep11_private_data_t *ep11_data, + const char *fname, const char *strval) +{ + if (strcmp(strval, "OFF") == 0) { + ep11_data->digest_libica = 0; + } else if (strcmp(strval, "DEFAULT") == 0) { + ep11_data->digest_libica = 1; + strcpy(ep11_data->digest_libica_path, ""); + } else { + if (strlen(strval) > + sizeof(ep11_data->digest_libica_path)-1) { + TRACE_ERROR("%s libica path is too long: '%s'\n", __func__, strval); + OCK_SYSLOG(LOG_ERR,"%s: Error: libica path '%s' is too long" + " in config file '%s'\n", __func__, strval, fname); + return CKR_FUNCTION_FAILED; + } + ep11_data->digest_libica = 1; + strncpy(ep11_data->digest_libica_path, strval, + sizeof(ep11_data->digest_libica_path)-1); + ep11_data->digest_libica_path[ + sizeof(ep11_data->digest_libica_path)-1] = '\0'; } + + return CKR_OK; } +static CK_RV ep11_config_set_wkvp(ep11_private_data_t *ep11_data, + const char *fname, const char *strval) +{ + unsigned int i, val; + + if (strncasecmp(strval, "0x", 2) == 0) + strval += 2; + + if (strlen(strval) < sizeof(ep11_data->expected_wkvp) * 2) { + TRACE_ERROR("%s expected WKVP is too short: '%s', expected %lu hex " + "characters in config file '%s'\n", __func__, strval, + sizeof(ep11_data->expected_wkvp) * 2, fname); + OCK_SYSLOG(LOG_ERR,"%s: Error: expected WKVP is too short: '%s', " + "expected %lu hex characters in config file '%s'\n", + __func__, strval, sizeof(ep11_data->expected_wkvp) * 2, + fname); + return CKR_FUNCTION_FAILED; + } + + if (strlen(strval) > sizeof(ep11_data->expected_wkvp) * 2) { + TRACE_INFO("%s only the first %lu characters of the expected WKVP in " + "config file '%s' are used: %s\n", __func__, + sizeof(ep11_data->expected_wkvp) * 2, fname, strval); + OCK_SYSLOG(LOG_INFO,"%s: Info: only the first %lu characters of the " + "expected WKVP in config file '%s' are used: %s\n", __func__, + sizeof(ep11_data->expected_wkvp) * 2, fname, strval); + } + + for (i = 0; i < sizeof(ep11_data->expected_wkvp); i++) { + if (sscanf(strval + (i * 2), "%02x", &val) != 1) { + TRACE_ERROR("%s failed to parse expected WKVP: '%s' at character " + "%u in config file '%s'\n", __func__, strval, (i * 2), + fname); + OCK_SYSLOG(LOG_ERR,"%s: Error: failed to parse expected WKVP: '%s' " + "at character %u in config file '%s'\n", __func__, + strval, (i * 2), fname); + return CKR_FUNCTION_FAILED; + } + ep11_data->expected_wkvp[i] = val; + } + ep11_data->expected_wkvp_set = 1; + + TRACE_DEBUG_DUMP("Expected WKVP: ", ep11_data->expected_wkvp, + sizeof(ep11_data->expected_wkvp)); -static int read_adapter_config_file(STDLL_TokData_t * tokdata, - const char *conf_name) + return CKR_OK; +} + +static CK_RV read_adapter_config_file(STDLL_TokData_t * tokdata, + const char *conf_name) { ep11_private_data_t *ep11_data = tokdata->private_data; FILE *ap_fp = NULL; /* file pointer adapter config file */ - int i, ap_file_size = 0; /* size adapter config file */ - char *token, *str; - char filebuf[EP11_CFG_FILE_SIZE]; - char line[1024]; + int i, k; int whitemode = 0; int anymode = 0; - int apqn_i = 0; /* how many APQN numbers */ /* Since the ep11 token config contains the path to libica that * will later be dlopen()ed, we cannot use a token config * directory from an untrusted environment. */ char *conf_dir = secure_getenv("OCK_EP11_TOKEN_DIR"); char fname[PATH_MAX]; - int rc = 0; + CK_RV rc = CKR_OK; char *cfg_dir; char cfgname[2*PATH_MAX + 1]; + struct ConfigBaseNode *c, *e, *config = NULL; + struct ConfigBareConstNode *bare; + struct ConfigNumPairListNode *list; + struct ConfigBareStringConstNode *barestr; + const char *strval; if (tokdata->initialized) - return 0; + return CKR_OK; memset(fname, 0, PATH_MAX); @@ -9389,19 +10957,12 @@ } } else { if (conf_name && strlen(conf_name) > 0) { - strncpy(fname, conf_name, sizeof(fname) - 1); + snprintf(fname, sizeof(fname), "%s/%s", OCK_CONFDIR, conf_name); fname[sizeof(fname) - 1] = '\0'; ap_fp = fopen(fname, "r"); - if (!ap_fp) { + if (!ap_fp) TRACE_DEVEL("%s fopen('%s') failed with errno %d\n", __func__, fname, errno); - snprintf(fname, sizeof(fname), "%s/%s", OCK_CONFDIR, conf_name); - fname[sizeof(fname) - 1] = '\0'; - ap_fp = fopen(fname, "r"); - if (!ap_fp) - TRACE_DEVEL("%s fopen('%s') failed with errno %d\n", - __func__, fname, errno); - } } else { snprintf(fname, sizeof(fname), "%s/%s", OCK_CONFDIR, EP11_DEFAULT_CFG_FILE); @@ -9418,39 +10979,17 @@ TRACE_ERROR("%s no valid EP 11 config file found\n", __func__); OCK_SYSLOG(LOG_ERR, "%s: Error: EP 11 config file '%s' not found\n", __func__, fname); - return APQN_FILE_INV; + return CKR_FUNCTION_FAILED; } TRACE_INFO("%s EP 11 token config file is '%s'\n", __func__, fname); - /* read config file line by line, - * ignore empty and # and copy rest into file buf - */ - memset(filebuf, 0, EP11_CFG_FILE_SIZE); - while (fgets((char *) line, sizeof(line), ap_fp)) { - char *p; - int len; - /* skip over leading spaces */ - for (p = line; *p == ' ' || *p == '\t'; p++); - /* if line is empty or starts with # skip line */ - len = strlen(p); - if (*p != '#' && *p != '\n' && len > 0) { - /* store line in buffer */ - if (ap_file_size + len < EP11_CFG_FILE_SIZE) { - memcpy(filebuf + ap_file_size, p, len); - ap_file_size += len; - } else { - TRACE_ERROR("%s EP 11 config file '%s' is too large\n", - __func__, fname); - fclose(ap_fp); - OCK_SYSLOG(LOG_ERR, - "%s: Error: EP 11 config file '%s' is too large\n", - __func__, fname); - return APQN_FILE_INV_FILE_SIZE; - } - } - } + rc = parse_configlib_file(ap_fp, &config, ep11_config_parse_error, 0); fclose(ap_fp); + if (rc != 0) { + TRACE_ERROR("Error parsing config file '%s'\n", fname); + return CKR_FUNCTION_FAILED; + } ep11_data->target_list.length = 0; ep11_data->pkey_mode = PKEY_MODE_DEFAULT; @@ -9459,283 +10998,223 @@ ep11_data->digest_libica = 1; strcpy(ep11_data->digest_libica_path, ""); - /* parse the file buf + /* Analyse the parsed config elements * please note, we still accept the LOGLEVEL entry * for compatibility reasons but just ignore it. */ - for (i = 0, str = filebuf; rc == 0; str = NULL) { - /* strtok tokenizes the string, - * delimiters are newline and whitespace. - */ - token = strtok(str, "\n\t "); - - if (i == 0) { - /* expecting APQN_ALLOWLIST or APQN_WHITELIST or APQN_ANY - or LOGLEVEL or eof */ - if (token == NULL) - break; - if (strncmp(token, "APQN_WHITELIST", 14) == 0 || - strncmp(token, "APQN_ALLOWLIST", 14) == 0) { - whitemode = 1; - i = 1; - } else if (strncmp(token, "APQN_ANY", 8) == 0) { - anymode = 1; - i = 0; - } else if (strncmp(token, "LOGLEVEL", 8) == 0) { - i = 3; - } else if (strncmp(token, "FORCE_SENSITIVE", 15) == 0) { - i = 0; - ep11_data->cka_sensitive_default_true = 1; - } else if (strncmp(token, "CPFILTER", 8) == 0) { - i = 4; - } else if (strncmp(token, "STRICT_MODE", 11) == 0) { - i = 0; - ep11_data->strict_mode = 1; - } else if (strncmp(token, "VHSM_MODE", 11) == 0) { - i = 0; - ep11_data->vhsm_mode = 1; - } else if (strncmp(token, "OPTIMIZE_SINGLE_PART_OPERATIONS", - 31) == 0) { - i = 0; - ep11_data->optimize_single_ops = 1; - } else if (strncmp(token, "PKEY_MODE", 9) == 0) { - i = 6; - } else if (strncmp(token, "DIGEST_LIBICA", 13) == 0) { - i = 5; - } else if (strncmp(token, "USE_PRANDOM", 11) == 0) { - i = 0; - token_specific.t_rng = NULL; - } else { - /* syntax error */ - TRACE_ERROR("%s Expected APQN_ALLOWLIST," - " APQN_ANY, LOGLEVEL, FORCE_SENSITIVE, CPFILTER," - " STRICT_MODE, VHSM_MODE, " - " OPTIMIZE_SINGLE_PART_OPERATIONS, PKEY_MODE, DIGEST_LIBICA, " - "or USE_PRANDOM keyword, found '%s' in config file " - "'%s'\n", __func__, - token, fname); - OCK_SYSLOG(LOG_ERR, "%s: Error: Expected APQN_ALLOWLIST," - " APQN_ANY, LOGLEVEL, FORCE_SENSITIVE, CPFILTER," - " STRICT_MODE, VHSM_MODE," - " OPTIMIZE_SINGLE_PART_OPERATIONS, PKEY_MODE, DIGEST_LIBICA, " - "or USE_PRANDOM keyword, found '%s' in config file " - "'%s'\n", - __func__, token, fname); - rc = APQN_FILE_SYNTAX_ERROR_0; - break; + confignode_foreach(c, config, i) { + TRACE_DEBUG("Config node: '%s' type: %u line: %u\n", + c->key, c->type, c->line); + + if (confignode_hastype(c, CT_FILEVERSION)) { + TRACE_DEBUG("Config file version: '%s'\n", + confignode_to_fileversion(c)->base.key); + continue; + } + + if (confignode_hastype(c, CT_STRINGVAL) || + confignode_hastype(c, CT_BAREVAL)) { + /* New style (key = value) tokens */ + strval = confignode_getstr(c); + + if (strcmp(c->key, "CPFILTER") == 0) { + rc = ep11_config_set_cpfilter(ep11_data, fname, strval); + if (rc != CKR_OK) + break; + continue; } - } else if (i == 1) { - /* expecting END or first number of a number - * pair (number range 0...255) - */ - if (token == NULL) { - rc = APQN_FILE_UNEXPECTED_END_OF_FILE; - OCK_SYSLOG(LOG_ERR, "%s: Error: Unexpected end of file found" - " in config file '%s', expected 'END' or adapter" - " number\n", - __func__, fname); - break; + + if (strcmp(c->key, "PKEY_MODE") == 0) { + rc = ep11_config_set_pkey_mode(ep11_data, fname, strval); + if (rc != CKR_OK) + break; + continue; } - if (strncmp(token, "END", 3) == 0) { - i = 0; - } else { - if (check_n(&ep11_data->target_list, token, &apqn_i) < 0) { - rc = APQN_FILE_SYNTAX_ERROR_1; - OCK_SYSLOG(LOG_ERR, "%s: Error: Expected valid adapter" - " number, found '%s' in config file '%s'\n", - __func__, token, fname); + + if (strcmp(c->key, "DIGEST_LIBICA") == 0) { + rc = ep11_config_set_libica(ep11_data, fname, strval); + if (rc != CKR_OK) break; - } - i = 2; + continue; } - } else if (i == 2) { - /* expecting second number of a number pair - * (number range 0...255) - */ - if (token == NULL) { - rc = APQN_FILE_UNEXPECTED_END_OF_FILE; - OCK_SYSLOG(LOG_ERR, "%s: Error: Unexpected end of file found" - " in config file '%s', expected domain number" - " (2nd number)\n", __func__, fname); - break; + + if (strcmp(c->key, "EXPECTED_WKVP") == 0) { + rc = ep11_config_set_wkvp(ep11_data, fname, strval); + if (rc != CKR_OK) + break; + continue; } - if (strncmp(token, "END", 3) == 0) { - TRACE_ERROR("%s Expected 2nd number, found '%s' in config " - "file\n", __func__, token); - OCK_SYSLOG(LOG_ERR, - "%s: Error: Expected valid domain" - " number (2nd number), found '%s' in config file" - " '%s'\n", __func__, token, fname); - rc = APQN_FILE_SYNTAX_ERROR_2; + } + + if (confignode_hastype(c, CT_NUMPAIRLIST)) { + list = confignode_to_numpairlist(c); + + if ((strcmp(list->base.key, "APQN_WHITELIST") != 0 && + strcmp(list->base.key, "APQN_ALLOWLIST") != 0) || + strcmp(list->end, "END") != 0) { + ep11_config_error_token(fname, list->base.key, list->base.line, + "APQN_ALLOWLIST ... END"); + rc = CKR_FUNCTION_FAILED; break; } - if (check_n(&ep11_data->target_list, token, &apqn_i) < 0) { - OCK_SYSLOG(LOG_ERR, "%s: Error: Expected valid domain" - " number (2nd number), found '%s' in config file" - " '%s'\n", __func__, token, fname); - rc = APQN_FILE_SYNTAX_ERROR_3; - break; + + whitemode = 1; + confignode_foreach(e, list->value, k) { + if (!confignode_hastype(e, CT_NUMPAIR)) { + ep11_config_error_token(fname, e->key, e->line, + "pair of NUMBERs"); + rc = CKR_FUNCTION_FAILED; + break; + } + + rc = ep11_config_add_apqn(ep11_data, confignode_to_numpair(e), + fname); + if (rc != CKR_OK) + break; } - ep11_data->target_list.length++; - if (ep11_data->target_list.length > MAX_APQN) { - TRACE_ERROR("%s Too many APQNs in config file (max %d)\n", - __func__, (int) MAX_APQN); - OCK_SYSLOG(LOG_ERR, - "%s: Error: Too many APQNs in config file '%s'\n", - __func__, fname); - rc = APQN_FILE_SYNTAX_ERROR_4; + if (rc != CKR_OK) break; - } - i = 1; - } else if (i == 3) { - /* expecting log level value - * (a number in the range 0...9) - */ - if (token == NULL) { - rc = APQN_FILE_UNEXPECTED_END_OF_FILE; - OCK_SYSLOG(LOG_ERR, "%s: Error: Unexpected end of file found" - " in config file '%s', expected LOGLEVEL value\n", - __func__, fname); + continue; + } + + if (!confignode_hastype(c, CT_BARECONST)) { + ep11_config_error_token(fname, c->key, c->line, NULL); + rc = CKR_FUNCTION_FAILED; + break; + } + + bare = confignode_to_bareconst(c); + + if (strcmp(bare->base.key, "APQN_ANY") == 0) { + anymode = 1; + continue; + } + + if (strcmp(bare->base.key, "FORCE_SENSITIVE") == 0) { + ep11_data->cka_sensitive_default_true = 1; + continue; + } + + if (strcmp(bare->base.key, "CPFILTER") == 0) { + rc = ep11_config_next(&c, CT_BARECONST | CT_BARESTRINGCONST, fname, + "CP-Filter config file name"); + if (rc != CKR_OK) break; - } - char *endptr; - int loglevel = strtol(token, &endptr, 10); - if (*endptr != '\0' || loglevel < 0 || loglevel > 9) { - TRACE_ERROR("%s Invalid loglevel value '%s' in config file\n", - __func__, token); - OCK_SYSLOG(LOG_ERR, - "%s: Error: Invalid LOGLEVEL value '%s' in config " - "file '%s'\n", - __func__, token, fname); - rc = APQN_FILE_SYNTAX_ERROR_5; + + if (confignode_hastype(c, CT_BARECONST)) + strval = confignode_to_bareconst(c)->base.key; + else + strval = confignode_to_barestringconst(c)->base.key; + + rc = ep11_config_set_cpfilter(ep11_data, fname,strval); + if (rc != CKR_OK) break; - } - TRACE_WARNING("%s LOGLEVEL setting is not supported any more !\n", - __func__); - TRACE_WARNING - ("%s Use opencryptoki logging/tracing facilities instead.\n", - __func__); - OCK_SYSLOG(LOG_WARNING, - "%s: Warning: LOGLEVEL setting is not supported any " - "more. Use opencryptoki logging/tracing facilities " - "instead.\n", __func__); - i = 0; - } else if (i == 4) { - /* expecting CP-filter config file name */ - if (token == NULL) { - rc = APQN_FILE_UNEXPECTED_END_OF_FILE; - OCK_SYSLOG(LOG_ERR, "%s: Error: Unexpected end of file found" - " in config file '%s', expected CP-Filter file " - "name\n", __func__, fname); + continue; + } + + if (strcmp(bare->base.key, "STRICT_MODE") == 0) { + ep11_data->strict_mode = 1; + continue; + } + + if (strcmp(bare->base.key, "VHSM_MODE") == 0) { + ep11_data->vhsm_mode = 1; + continue; + } + + if (strcmp(bare->base.key, "OPTIMIZE_SINGLE_PART_OPERATIONS") == 0) { + ep11_data->optimize_single_ops = 1; + continue; + } + + if (strcmp(bare->base.key, "PKEY_MODE") == 0) { + rc = ep11_config_next(&c, CT_BARECONST, fname, "PKEY mode"); + if (rc != CKR_OK) break; - } - if (strlen(token) > - sizeof(ep11_data->cp_filter_config_filename) - 1) { - TRACE_ERROR("%s CP-Filter config file name is too long: '%s'\n", - __func__, token); - OCK_SYSLOG(LOG_ERR, - "%s: Error: CP-Filter config file name '%s' is too " - "long in config file '%s'\n", - __func__, token, fname); - rc = APQN_FILE_SYNTAX_ERROR_6; + + rc = ep11_config_set_pkey_mode(ep11_data, fname, + confignode_to_bareconst(c)->base.key); + if (rc != CKR_OK) break; - } - strncpy(ep11_data->cp_filter_config_filename, token, - sizeof(ep11_data->cp_filter_config_filename) - 1); - ep11_data->cp_filter_config_filename[ - sizeof(ep11_data->cp_filter_config_filename) - 1] = '\0'; - i = 0; - } else if (i == 5) { - /* expecting libica path, 'DEFAULT', or 'OFF' */ - if (token == NULL) { - rc = APQN_FILE_UNEXPECTED_END_OF_FILE; - OCK_SYSLOG(LOG_ERR,"%s: Error: Unexpected end of file found" - " in config file '%s', expected libica path, " - "'DEFAULT', or 'OFF'\n", - __func__, fname); + continue; + } + + if (strcmp(bare->base.key, "DIGEST_LIBICA") == 0) { + rc = ep11_config_next(&c, CT_BARECONST | CT_BARESTRINGCONST, fname, + "libica path, 'DEFAULT', or 'OFF'"); + if (rc != CKR_OK) break; - } - if (strcmp(token, "OFF") == 0) { - ep11_data->digest_libica = 0; - } else if (strcmp(token, "DEFAULT") == 0) { - ep11_data->digest_libica = 1; - strcpy(ep11_data->digest_libica_path, ""); - } else { - if (strlen(token) > sizeof(ep11_data->digest_libica_path)-1) { - TRACE_ERROR("%s libica path is too long: '%s'\n", - __func__, token); - OCK_SYSLOG(LOG_ERR,"%s: Error: libica path '%s' is too long" - " in config file '%s'\n", - __func__, token, fname); - rc = APQN_FILE_SYNTAX_ERROR_6; - break; - } - ep11_data->digest_libica = 1; - strncpy(ep11_data->digest_libica_path, token, - sizeof(ep11_data->digest_libica_path)-1); - ep11_data->digest_libica_path[sizeof(ep11_data->digest_libica_path)-1] = '\0'; - } - i = 0; - } else if (i == 6) { - /* expecting pkey_mode */ - if (token == NULL) { - rc = APQN_FILE_UNEXPECTED_END_OF_FILE; - OCK_SYSLOG(LOG_ERR,"%s: Error: Unexpected end of file found" - " in config file '%s', expected pkey_mode 0 .. 3\n", - __func__, fname); + + if (confignode_hastype(c, CT_BARECONST)) + strval = confignode_to_bareconst(c)->base.key; + else + strval = confignode_to_barestringconst(c)->base.key; + + rc = ep11_config_set_libica(ep11_data, fname,strval); + if (rc != CKR_OK) break; - } - if (strncmp(token, "DISABLED", 8) == 0) - ep11_data->pkey_mode = PKEY_MODE_DISABLED; - else if (strncmp(token, "DEFAULT", 7) == 0) - ep11_data->pkey_mode = PKEY_MODE_DEFAULT; - else if (strncmp(token, "ENABLE4NONEXTR", 14) == 0) - ep11_data->pkey_mode = PKEY_MODE_ENABLE4NONEXTR; - else { - TRACE_ERROR("%s unsupported pkey mode : '%s'\n", - __func__, token); - OCK_SYSLOG(LOG_ERR,"%s: Error: unsupported pkey mode '%s' in config file '%s'\n", - __func__, token, fname); - rc = APQN_FILE_SYNTAX_ERROR_6; + continue; + } + + if (strcmp(bare->base.key, "USE_PRANDOM") == 0) { + token_specific.t_rng = NULL; + continue; + } + + if (strcmp(bare->base.key, "EXPECTED_WKVP") == 0) { + rc = ep11_config_next(&c, CT_BARESTRINGCONST, fname, + "WKID as quoted hex string"); + if (rc != CKR_OK) break; - } - i = 0; + barestr = confignode_to_barestringconst(c); + + rc = ep11_config_set_wkvp(ep11_data, fname, barestr->base.key); + if (rc != CKR_OK) + break; + continue; } + + ep11_config_error_token(fname, c->key, c->line, NULL); + rc = CKR_FUNCTION_FAILED; + break; } + confignode_deepfree(config); + + if (rc != CKR_OK) + return rc; + /* do some checks: */ - if (rc == 0) { - if (!(whitemode || anymode)) { - TRACE_ERROR("%s At least one APQN mode needs to be present in " - "config file: APQN_ALLOWLIST or APQN_ANY\n", __func__); - OCK_SYSLOG(LOG_ERR, - "%s: Error: At least one APQN mode needs to be present " - " in config file '%s': APQN_ALLOWLIST or APQN_ANY\n", - __func__, fname); - rc = APQN_FILE_NO_APQN_MODE; - } else if (whitemode && anymode) { - TRACE_ERROR("%s Only one APQN mode can be present in config file:" - " APQN_ALLOWLIST or APQN_ANY\n", __func__); + if (!(whitemode || anymode)) { + TRACE_ERROR("%s At least one APQN mode needs to be present in " + "config file: APQN_ALLOWLIST or APQN_ANY\n", __func__); + OCK_SYSLOG(LOG_ERR, + "%s: Error: At least one APQN mode needs to be present " + " in config file '%s': APQN_ALLOWLIST or APQN_ANY\n", + __func__, fname); + return CKR_FUNCTION_FAILED; + } else if (whitemode && anymode) { + TRACE_ERROR("%s Only one APQN mode can be present in config file:" + " APQN_ALLOWLIST or APQN_ANY\n", __func__); + OCK_SYSLOG(LOG_ERR, + "%s: Error: Only one APQN mode can be present in" + " config file '%s': APQN_ALLOWLIST or APQN_ANY\n", + __func__, fname); + return CKR_FUNCTION_FAILED; + } else if (whitemode) { + /* at least one APQN needs to be defined */ + if (ep11_data->target_list.length < 1) { + TRACE_ERROR("%s At least one APQN needs to be defined in the " + "config file\n", __func__); OCK_SYSLOG(LOG_ERR, - "%s: Error: Only one APQN mode can be present in" - " config file '%s': APQN_ALLOWLIST or APQN_ANY\n", - __func__, fname); - rc = APQN_FILE_NO_APQN_MODE; - } else if (whitemode) { - /* at least one APQN needs to be defined */ - if (ep11_data->target_list.length < 1) { - TRACE_ERROR("%s At least one APQN needs to be defined in the " - "config file\n", __func__); - OCK_SYSLOG(LOG_ERR, - "%s: Error: At least one APQN needs to be defined in" - " config file '%s'\n", __func__, fname); - rc = APQN_FILE_NO_APQN_GIVEN; - } + "%s: Error: At least one APQN needs to be defined in" + " config file '%s'\n", __func__, fname); + return CKR_FUNCTION_FAILED; } } /* log the whitelist of APQNs */ - if (rc == 0 && whitemode) { + if (whitemode) { TRACE_INFO("%s whitelist with %d APQNs defined:\n", __func__, ep11_data->target_list.length); for (i = 0; i < ep11_data->target_list.length; i++) { @@ -9746,38 +11225,34 @@ } /* read CP-filter config file */ - if (rc == 0) { - cfg_dir = dirname(fname); - if (strlen(ep11_data->cp_filter_config_filename) == 0) { - snprintf(ep11_data->cp_filter_config_filename, - sizeof(ep11_data->cp_filter_config_filename) - 1, - "%s/%s", cfg_dir, EP11_DEFAULT_CPFILTER_FILE); - ep11_data->cp_filter_config_filename[ - sizeof(ep11_data->cp_filter_config_filename) - 1] = '\0'; - } - - if (strchr(ep11_data->cp_filter_config_filename, '/') == NULL) { - cfgname[0] = '\0'; - - if (strlen(cfg_dir) + 1 - + strlen(ep11_data->cp_filter_config_filename) - <= sizeof(cfgname) - 1) { - strcpy(cfgname, cfg_dir); - cfgname[strlen(cfg_dir)] = '/'; - strcpy(cfgname + strlen(cfg_dir) + 1, - ep11_data->cp_filter_config_filename); - } - if (strlen(cfgname) < sizeof(ep11_data->cp_filter_config_filename)) - strcpy(ep11_data->cp_filter_config_filename, cfgname); - ep11_data->cp_filter_config_filename[ - sizeof(ep11_data->cp_filter_config_filename) - 1] = '\0'; - } - - rc = read_cp_filter_config_file(tokdata, - ep11_data->cp_filter_config_filename, - &ep11_data->cp_config); - } - + cfg_dir = dirname(fname); + if (strlen(ep11_data->cp_filter_config_filename) == 0) { + snprintf(ep11_data->cp_filter_config_filename, + sizeof(ep11_data->cp_filter_config_filename) - 1, + "%s/%s", cfg_dir, EP11_DEFAULT_CPFILTER_FILE); + ep11_data->cp_filter_config_filename[ + sizeof(ep11_data->cp_filter_config_filename) - 1] = '\0'; + } + + if (strchr(ep11_data->cp_filter_config_filename, '/') == NULL) { + cfgname[0] = '\0'; + + if (strlen(cfg_dir) + 1 + strlen(ep11_data->cp_filter_config_filename) + <= sizeof(cfgname) - 1) { + strcpy(cfgname, cfg_dir); + cfgname[strlen(cfg_dir)] = '/'; + strcpy(cfgname + strlen(cfg_dir) + 1, + ep11_data->cp_filter_config_filename); + } + if (strlen(cfgname) < sizeof(ep11_data->cp_filter_config_filename)) + strcpy(ep11_data->cp_filter_config_filename, cfgname); + ep11_data->cp_filter_config_filename[ + sizeof(ep11_data->cp_filter_config_filename) - 1] = '\0'; + } + + rc = read_cp_filter_config_file(tokdata, + ep11_data->cp_filter_config_filename, + &ep11_data->cp_config); return rc; } @@ -9787,11 +11262,11 @@ #define CP_BIT_IN_BYTE(cp) ((cp) % 8) #define CP_BIT_MASK(cp) (0x80 >> CP_BIT_IN_BYTE(cp)) -static int read_cp_filter_config_file(STDLL_TokData_t *tokdata, - const char *conf_name, - cp_config_t ** cp_config) +static CK_RV read_cp_filter_config_file(STDLL_TokData_t *tokdata, + const char *conf_name, + cp_config_t ** cp_config) { - int rc = 0; + CK_RV rc = CKR_OK; FILE *fp = NULL; char line[1024]; char *tok; @@ -9814,7 +11289,7 @@ conf_name); /* this is not an error condition. When no CP-filter file is available, * then the mechanisms are not filtered. */ - return 0; + return CKR_OK; } while (fgets((char *) line, sizeof(line), fp)) { @@ -9835,7 +11310,7 @@ "%s: Error: Expected valid control point name or " "number, found '%s' in CP-filter config file '%s'\n", __func__, tok, conf_name); - rc = APQN_FILE_SYNTAX_ERROR_7; + rc = CKR_FUNCTION_FAILED; goto out_fclose; } } @@ -9843,7 +11318,7 @@ cp = (cp_config_t *) malloc(sizeof(cp_config_t)); if (cp == NULL) { TRACE_ERROR("%s Out of memory.\n", __func__); - rc = APQN_OUT_OF_MEMORY; + rc = CKR_HOST_MEMORY; goto out_fclose; } cp->cp = val; @@ -9865,7 +11340,7 @@ "%s: Error: Expected valid mechanism name or " "number, found '%s' in CP-filter config file " "'%s'\n", __func__, tok, conf_name); - rc = APQN_FILE_SYNTAX_ERROR_8; + rc = CKR_FUNCTION_FAILED; free_cp_config(cp); goto out_fclose; } @@ -9877,7 +11352,7 @@ OCK_SYSLOG(LOG_ERR, "%s: Error: Out of memory while parsing the" " CP-filter config file '%s'\n", __func__, conf_name); - rc = APQN_OUT_OF_MEMORY; + rc = CKR_HOST_MEMORY; free_cp_config(cp); goto out_fclose; } @@ -9996,11 +11471,20 @@ CONSTINFO(XCP_CPB_WRAP_WITH_RAW_SPKI), CONSTINFO(XCP_CPB_ALG_DH), CONSTINFO(XCP_CPB_DERIVE), + CONSTINFO(XCP_CPB_ALLOW_NONSESSION), CONSTINFO(XCP_CPB_ALG_EC_25519), + CONSTINFO(XCP_CPB_ALG_EC_SECGCRV), CONSTINFO(XCP_CPB_ALG_NBSI2017), CONSTINFO(XCP_CPB_CPACF_PK), CONSTINFO(XCP_CPB_ALG_PQC_DILITHIUM), CONSTINFO(XCP_CPB_ALG_PQC), + CONSTINFO(XCP_CPB_BTC), + CONSTINFO(XCP_CPB_ECDSA_OTHER), + CONSTINFO(XCP_CPB_ALG_NFIPS2021), + CONSTINFO(XCP_CPB_ALG_NFIPS2024), + CONSTINFO(XCP_CPB_COMPAT_LEGACY_SHA3), + CONSTINFO(XCP_CPB_DSA_PARAMETER_GEN), + CONSTINFO(XCP_CPB_DERIVE_NON_AB_KEYS), }; #ifdef DEBUG @@ -10269,8 +11753,8 @@ unsigned char cmd[100]; struct XCPadmresp rb; size_t rlen, clen; - long rc; - CK_RV rv = 0; + CK_RV rc = 0; + long len; target_t target; CK_IBM_XCP_INFO xcp_info; CK_ULONG xcp_info_len = sizeof(xcp_info); @@ -10280,29 +11764,28 @@ return rc; memset(cmd, 0, sizeof(cmd)); - rc = dll_xcpa_queryblock(cmd, sizeof(cmd), XCP_ADMQ_DOM_CTRLPOINTS, + len = dll_xcpa_queryblock(cmd, sizeof(cmd), XCP_ADMQ_DOM_CTRLPOINTS, (uint64_t) adapter << 32 | domain, NULL, 0); - if (rc < 0) { - TRACE_ERROR("%s xcpa_queryblock failed: rc=%ld\n", __func__, rc); + if (len < 0) { + TRACE_ERROR("%s xcpa_queryblock failed: rc=%ld\n", __func__, len); rc = CKR_DEVICE_ERROR; goto out; } - clen = rc; + clen = len; memset(rsp, 0, sizeof(rsp)); rlen = sizeof(rsp); rc = dll_m_admin(rsp, &rlen, NULL, NULL, cmd, clen, NULL, 0, target); - if (rc < 0) { + if (rc != CKR_OK) { TRACE_ERROR("%s m_admin rc=%ld\n", __func__, rc); - rc = CKR_DEVICE_ERROR; goto out; } memset(&rb, 0, sizeof(rb)); - rc = dll_xcpa_internal_rv(rsp, rlen, &rb, &rv); - if (rc < 0 || rv != 0) { - TRACE_ERROR("%s xcpa_internal_rv failed: rc=%ld rv=%ld\n", - __func__, rc, rv); + len = dll_xcpa_internal_rv(rsp, rlen, &rb, &rc); + if (len < 0 || rc != 0) { + TRACE_ERROR("%s xcpa_internal_rv failed: rc=%ld len=%ld\n", + __func__, rc, len); rc = CKR_DEVICE_ERROR; goto out; } @@ -10368,13 +11851,18 @@ #ifdef DEBUG TRACE_DEBUG("Control points from adapter %02X.%04X\n", adapter, domain); TRACE_DEBUG_DUMP(" ", cp, cp_len); + TRACE_DEBUG("Max control point index: %lu\n", max_cp_index); #endif if (data->first) { data->first_adapter = adapter; data->first_domain = domain; - memcpy(data->first_cp, cp, cp_len); - memcpy(data->combined_cp, cp, cp_len); + /* Apply CP bits 0 to max_cp_index only */ + for (i = 0; i <= max_cp_index; i++) { + data->combined_cp[CP_BYTE_NO(i)] &= + (cp[CP_BYTE_NO(i)] | ~CP_BIT_MASK(i)); + } + memcpy(data->first_cp, data->combined_cp, sizeof(data->first_cp)); data->max_cp_index = max_cp_index; data->first = 0; } else { @@ -10391,8 +11879,10 @@ data->first_domain); } - for (i = 0; i < cp_len; i++) { - data->combined_cp[i] &= cp[i]; + for (i = 0; i <= max_cp_index; i++) { + /* Apply CP bits 0 to max_cp_index only */ + data->combined_cp[CP_BYTE_NO(i)] &= + (cp[CP_BYTE_NO(i)] | ~CP_BIT_MASK(i)); } if (max_cp_index != data->max_cp_index) { @@ -10437,6 +11927,11 @@ ep11_private_data_t *ep11_data = tokdata->private_data; memset(&data, 0, sizeof(data)); + /* + * Turn all CPs ON by default, so that newer control points that are unknown + * to older cards default to ON. CPs being OFF disable functionality. + */ + memset(data.combined_cp, 0xff, sizeof(data.combined_cp)); data.first = 1; rc = handle_all_ep11_cards(&ep11_data->target_list, control_point_handler, &data); @@ -10451,6 +11946,7 @@ TRACE_DEBUG("Combined control points from all cards (%lu CPs):\n", data.max_cp_index); TRACE_DEBUG_DUMP(" ", cp, *cp_len); + TRACE_DEBUG("Max control point index: %lu\n", data.max_cp_index); print_control_points(cp, *cp_len, data.max_cp_index); #endif @@ -10478,7 +11974,8 @@ CK_ULONG ulCount); CK_RV SC_OpenSession(STDLL_TokData_t * tokdata, CK_SLOT_ID sid, CK_FLAGS flags, CK_SESSION_HANDLE_PTR phSession); -CK_RV SC_CloseSession(STDLL_TokData_t * tokdata, ST_SESSION_HANDLE * sSession); +CK_RV SC_CloseSession(STDLL_TokData_t * tokdata, ST_SESSION_HANDLE * sSession, + CK_BBOOL in_fork_initializer); static CK_RV generate_ep11_session_id(STDLL_TokData_t * tokdata, SESSION * session, @@ -10687,6 +12184,7 @@ TRACE_ERROR("%s dll_m_Login failed: 0x%lx\n", __func__, rc); /* ignore the error here, the adapter may not be able to perform * m_Login at this moment */ + rc = CKR_OK; goto strict_mode; } #ifdef DEBUG @@ -10958,7 +12456,7 @@ } if (helper_session != CK_INVALID_HANDLE) { - rc2 = ep11_close_helper_session(tokdata, &handle); + rc2 = ep11_close_helper_session(tokdata, &handle, FALSE); if (rc2 != CKR_OK) TRACE_ERROR("%s ep11_close_helper_session failed: 0x%lx\n", __func__, rc2); @@ -11056,7 +12554,7 @@ session->private_data = NULL; if (helper_session != CK_INVALID_HANDLE) { - rc2 = ep11_close_helper_session(tokdata, &handle); + rc2 = ep11_close_helper_session(tokdata, &handle, in_fork_initializer); if (rc2 != CKR_OK) TRACE_ERROR("%s ep11_close_helper_session failed: 0x%lx\n", __func__, rc2); @@ -11120,13 +12618,14 @@ } static CK_RV ep11_close_helper_session(STDLL_TokData_t * tokdata, - ST_SESSION_HANDLE * sSession) + ST_SESSION_HANDLE * sSession, + CK_BBOOL in_fork_initializer) { CK_RV rc; TRACE_INFO("%s\n", __func__); - rc = SC_CloseSession(tokdata, sSession); + rc = SC_CloseSession(tokdata, sSession, in_fork_initializer); if (rc != CKR_OK) TRACE_ERROR("%s SC_CloseSession failed: 0x%lx\n", __func__, rc); @@ -11208,6 +12707,7 @@ CK_CHAR serialNumber[16]; CK_BBOOL first; CK_BBOOL error; + CK_BYTE pqc_strength[PQC_BYTES]; } query_version_t; static CK_RV version_query_handler(uint_32 adapter, uint_32 domain, @@ -11216,9 +12716,11 @@ query_version_t *qv = (query_version_t *)handler_data; CK_IBM_XCP_INFO xcp_info; CK_ULONG xcp_info_len = sizeof(xcp_info); + CK_BYTE pqc_strength[PQC_BYTES] = { 0 }; + CK_ULONG pqc_strength_len = sizeof(pqc_strength); CK_RV rc; target_t target; - CK_ULONG card_type; + CK_ULONG card_type, i; ep11_card_version_t *card_version; rc = get_ep11_target_for_apqn(adapter, domain, &target, 0); @@ -11334,6 +12836,30 @@ if (qv->first) memcpy(qv->serialNumber, xcp_info.serialNumber, sizeof(qv->serialNumber)); + + /* Query for PQC strength support. If the PQC strength query is not + available only Dilithium 6-5 round 2 is available. */ + rc = dll_m_get_xcp_info(&pqc_strength, &pqc_strength_len, + CK_IBM_XCPQ_PQC_STRENGTHS, 0, target); + if (rc != CKR_OK) { + TRACE_DEVEL("%s Failed to query PQC-strength from adapter %02X.%04X\n", + __func__, adapter, domain); + /* Only R2_65 is available */ + pqc_strength[PQC_BYTE_NO(XCP_PQC_S_DILITHIUM_R2_65)] |= + PQC_BIT_MASK(XCP_PQC_S_DILITHIUM_R2_65); + rc = CKR_OK; + } + + TRACE_DEBUG("PQC-strength of %02X.%04X:\n", adapter, domain); + TRACE_DEBUG_DUMP("", pqc_strength, sizeof(qv->pqc_strength)); + + if (qv->first) { + memcpy(qv->pqc_strength, pqc_strength, sizeof(qv->pqc_strength)); + } else { + for (i = 0; i < sizeof(qv->pqc_strength); i++) + qv->pqc_strength[i] &= pqc_strength[i]; + } + qv->first = FALSE; out: @@ -11391,6 +12917,7 @@ ep11_private_data_t *ep11_data = tokdata->private_data; ep11_card_version_t *card_version; query_version_t qv; + CK_ULONG i; CK_RV rc; memset(&qv, 0, sizeof(qv)); @@ -11448,6 +12975,14 @@ TRACE_INFO("%s Used Firmware API: %lu\n", __func__, target_info->used_firmware_API_version); + memcpy(target_info->pqc_strength, qv.pqc_strength, sizeof(qv.pqc_strength)); + + TRACE_INFO("Combined PQC-strength:\n"); + for (i = 1; i <= XCP_PQC_MAX; i++) { + TRACE_INFO(" Strength %lu: %d\n", i, + (qv.pqc_strength[PQC_BYTE_NO(i)] & PQC_BIT_MASK(i)) != 0); + } + return CKR_OK; } @@ -11464,6 +12999,113 @@ } } +typedef struct query_wkvp +{ + ep11_private_data_t *ep11_data; + ep11_target_info_t *target_info; + CK_BBOOL error; +} query_wkvp_t; + +const unsigned char ep11_zero_mkvp[XCP_WKID_BYTES] = { 0 }; + +static CK_RV wkvp_query_handler(uint_32 adapter, uint_32 domain, + void *handler_data) +{ + query_wkvp_t *qw = (query_wkvp_t *)handler_data; + CK_IBM_DOMAIN_INFO domain_info; + CK_ULONG domain_info_len = sizeof(domain_info); + CK_RV rc; + target_t target; + + rc = get_ep11_target_for_apqn(adapter, domain, &target, 0); + if (rc != CKR_OK) + return rc; + + rc = dll_m_get_xcp_info(&domain_info, &domain_info_len, CK_IBM_XCPQ_DOMAIN, + 0, target); + if (rc != CKR_OK) { + TRACE_ERROR("%s Failed to query domain info from APQN %02X.%04X\n", + __func__, adapter, domain); + /* card may no longer be online, so ignore this error situation */ + rc = CKR_OK; + goto out; + } + + if ((domain_info.flags & CK_IBM_DOM_CURR_WK) == 0) { + TRACE_ERROR("%s No EP11 wrapping key is set on APQN %02X.%04X\n", + __func__, adapter, domain); + OCK_SYSLOG(LOG_ERR, "%s No EP11 wrapping key is set on APQN %02X.%04X\n", + __func__, adapter, domain); + qw->error = TRUE; + rc = CKR_OK; + goto out; + } + + TRACE_DEBUG("%s WKVP of APQN %02X.%04X:\n", __func__, adapter, domain); + TRACE_DEBUG_DUMP("full WKVP: ", domain_info.wk, sizeof( domain_info.wk)); + + if (qw->ep11_data->expected_wkvp_set == FALSE && + memcmp(qw->ep11_data->expected_wkvp, ep11_zero_mkvp, + XCP_WKID_BYTES) == 0) { + /* zero expected MKVP, copy current one */ + memcpy(qw->ep11_data->expected_wkvp, domain_info.wk, XCP_WKID_BYTES); + } else { + if (memcmp(domain_info.wk, qw->ep11_data->expected_wkvp, + XCP_WKID_BYTES) != 0) { + TRACE_ERROR("EP11 wrapping key on APQN %02X.%04X does not " + "match the %s wrapping key\n", adapter, domain, + qw->ep11_data->expected_wkvp_set ? + "expected" : "other APQN's"); + OCK_SYSLOG(LOG_ERR, "EP11 wrapping key on APQN %02X.%04X does not " + "match the %s wrapping key\n", adapter, domain, + qw->ep11_data->expected_wkvp_set ? + "expected" : "other APQN's"); + qw->error = TRUE; + rc = CKR_OK; + goto out; + } + } + +out: + free_ep11_target_for_apqn(target); + return rc; +} + +static CK_RV ep11tok_check_wkvps(STDLL_TokData_t *tokdata, + ep11_target_info_t *target_info) +{ + ep11_private_data_t *ep11_data = tokdata->private_data; + query_wkvp_t qw; + CK_RV rc; + + memset(&qw, 0, sizeof(qw)); + qw.ep11_data = ep11_data; + qw.target_info = target_info; + + rc = handle_all_ep11_cards(&ep11_data->target_list, wkvp_query_handler, + &qw); + if (rc != CKR_OK) { + TRACE_ERROR("%s handle_all_ep11_cards failed: rc=0x%lx\n", + __func__, rc); + return rc; + } + + if (qw.error) { + TRACE_ERROR("%s Errors occurred during WKVP query\n", __func__); + return CKR_DEVICE_ERROR; + } + + if (ep11_data->expected_wkvp_set == FALSE) { + TRACE_DEBUG_DUMP("WKVP (queried): ", ep11_data->expected_wkvp, + XCP_WKID_BYTES); + } else { + TRACE_DEBUG_DUMP("WKVP (config): ", ep11_data->expected_wkvp, + XCP_WKID_BYTES); + } + + return CKR_OK; +} + CK_RV ep11tok_copy_firmware_info(STDLL_TokData_t *tokdata, CK_TOKEN_INFO_PTR pInfo) { @@ -11760,11 +13402,14 @@ } } -CK_RV token_specific_set_attribute_values(STDLL_TokData_t *tokdata, OBJECT *obj, +CK_RV token_specific_set_attribute_values(STDLL_TokData_t *tokdata, + SESSION *session, + OBJECT *obj, TEMPLATE *new_tmpl) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_OBJECT_CLASS class; + CK_KEY_TYPE ktype; size_t keyblobsize = 0; CK_BYTE *keyblob; DL_NODE *node; @@ -11773,7 +13418,6 @@ CK_ULONG num_attributes = 0; CK_ATTRIBUTE *attr; CK_RV rc; - ep11_target_info_t* target_info; rc = template_attribute_get_ulong(obj->template, CKA_CLASS, &class); if (rc != CKR_OK) { @@ -11791,6 +13435,12 @@ return CKR_OK; } + rc = template_attribute_get_ulong(obj->template, CKA_KEY_TYPE, &ktype); + if (rc != CKR_OK) { + TRACE_ERROR("%s CKA_KEY_TYPE is missing\n", __func__); + return rc; + } + rc = obj_opaque_2_blob(tokdata, obj, &keyblob, &keyblobsize); if (rc != CKR_OK) { TRACE_ERROR("%s no key-blob rc=0x%lx\n", __func__, rc); @@ -11859,25 +13509,40 @@ goto out; } - target_info = get_target_info(tokdata); - if (target_info == NULL) { - rc = CKR_FUNCTION_FAILED; - goto out; - } - - rc = dll_m_SetAttributeValue(ibm_opaque_attr->pValue, - ibm_opaque_attr->ulValueLen, attributes, - num_attributes, target_info->target); - - put_target_info(tokdata, target_info); + RETRY_START(rc, tokdata) + rc = dll_m_SetAttributeValue(ibm_opaque_attr->pValue, + (ktype != CKK_AES_XTS ? + ibm_opaque_attr->ulValueLen : + ibm_opaque_attr->ulValueLen / 2), + attributes, num_attributes, + target_info->target); + RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { rc = ep11_error_to_pkcs11_error(rc, NULL); TRACE_ERROR("%s m_SetAttributeValue failed rc=0x%lx\n", __func__, rc); + free(ibm_opaque_attr); goto out; } + if (ktype == CKK_AES_XTS) { + RETRY_START(rc, tokdata) + rc = dll_m_SetAttributeValue((CK_BYTE *)ibm_opaque_attr->pValue + + (ibm_opaque_attr->ulValueLen / 2), + ibm_opaque_attr->ulValueLen / 2, + attributes, num_attributes, + target_info->target); + RETRY_END(rc, tokdata, session) + + if (rc != CKR_OK) { + rc = ep11_error_to_pkcs11_error(rc, NULL); + TRACE_ERROR("%s m_SetAttributeValue failed rc=0x%lx\n", + __func__, rc); + free(ibm_opaque_attr); + goto out; + } + } rc = template_update_attribute(new_tmpl, ibm_opaque_attr); if (rc != CKR_OK) { TRACE_ERROR("%s template_update_attribute failed rc=0x%lx\n", @@ -11936,13 +13601,20 @@ rc = refresh_target_info(tokdata); if (rc != CKR_OK) { - TRACE_ERROR("%s Failed to get the target infos (refresh_target_info " + TRACE_DEVEL("%s Failed to get the target infos (refresh_target_info " "rc=0x%lx)\n", __func__, rc); - OCK_SYSLOG(LOG_ERR, "%s: Failed to get the target info rc=0x%lx\n", - __func__, rc); + + TRACE_ERROR("EP11 APQN setup is inconsistent, all crypto operations " + "will fail from now on\n"); + OCK_SYSLOG(LOG_ERR, "EP11 APQN setup is inconsistent, all crypto " + "operations will fail from now on\n"); + + __sync_or_and_fetch(&ep11_data->inconsistent, 1); return rc; } + __sync_and_and_fetch(&ep11_data->inconsistent, 0); + return CKR_OK; } @@ -11997,9 +13669,14 @@ target_info->ref_count = 1; + /* Get and check the WKVPs freshly with the current set of APQNs */ + rc = ep11tok_check_wkvps(tokdata, target_info); + if (rc != CKR_OK) + goto error; + /* Get the version info freshly with the current set of APQNs */ rc = ep11tok_get_ep11_version(tokdata, target_info); - if (rc != 0) + if (rc != CKR_OK) goto error; /* Get the control points freshly with the current set of APQNs */ @@ -12007,7 +13684,7 @@ rc = get_control_points(tokdata, target_info->control_points, &target_info->control_points_len, &target_info->max_control_point_index); - if (rc != 0) + if (rc != CKR_OK) goto error; /* Setup the group target freshly with the current set of APQNs */ @@ -12069,6 +13746,8 @@ target_info = *((void * volatile *)&ep11_data->target_info); if (target_info == NULL) { TRACE_ERROR("%s: target_info is NULL\n", __func__); + if (pthread_rwlock_unlock(&ep11_data->target_rwlock) != 0) + TRACE_DEVEL("Target Unlock failed.\n"); return NULL; } @@ -12130,7 +13809,8 @@ * object_mgr_create_final. */ static CK_RV update_ep11_attrs_from_blob(STDLL_TokData_t *tokdata, - TEMPLATE *tmpl) + SESSION *session, TEMPLATE *tmpl, + CK_BBOOL aes_xts) { ep11_private_data_t *ep11_data = tokdata->private_data; CK_BBOOL restr = CK_FALSE; /*, never_mod = CK_FALSE; */ @@ -12138,7 +13818,6 @@ CK_BBOOL pkeyextr = CK_FALSE, pkeyneverextr = CK_FALSE; CK_ULONG stdcomp1 = 0; CK_ATTRIBUTE *attr, *blob_attr = NULL; - ep11_target_info_t* target_info; CK_RV rc = CKR_OK; CK_ULONG i; @@ -12165,15 +13844,12 @@ return CKR_FUNCTION_FAILED; } - target_info = get_target_info(tokdata); - if (target_info == NULL) - return CKR_FUNCTION_FAILED; - - rc = dll_m_GetAttributeValue(blob_attr->pValue, - blob_attr->ulValueLen, ibm_attrs, - num_ibm_attrs, target_info->target); - - put_target_info(tokdata, target_info); + RETRY_START(rc, tokdata) + rc = dll_m_GetAttributeValue(blob_attr->pValue, + (aes_xts ? blob_attr->ulValueLen / 2 : + blob_attr->ulValueLen), + ibm_attrs, num_ibm_attrs, target_info->target); + RETRY_END(rc, tokdata, session) if (rc != CKR_OK) { rc = ep11_error_to_pkcs11_error(rc, NULL); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11_specific.h opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11_specific.h --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11_specific.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11_specific.h 2023-02-13 09:22:42.000000000 +0100 @@ -53,6 +53,12 @@ CK_OBJECT_HANDLE_PTR phPublicKey, CK_OBJECT_HANDLE_PTR phPrivateKey); +CK_RV ep11tok_check_single_mech_key(STDLL_TokData_t *tokdata, SESSION * session, + CK_MECHANISM *mech, CK_OBJECT_HANDLE key, + CK_ULONG operation); + +CK_BOOL ep11tok_mech_single_only(CK_MECHANISM *mech); + CK_RV ep11tok_sign_init(STDLL_TokData_t * tokdata, SESSION * session, CK_MECHANISM * mech, CK_BBOOL recover_mode, CK_OBJECT_HANDLE key); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11_stdll.mk opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11_stdll.mk --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11_stdll.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11_stdll.mk 2023-02-13 09:22:42.000000000 +0100 @@ -6,13 +6,14 @@ usr/lib/ep11_stdll/tok_struct.h opencryptoki_stdll_libpkcs11_ep11_la_CFLAGS = \ - -DDEV -D_THREAD_SAFE -DSHALLOW=0 -DEPSWTOK=1 -DLITE=0 -DNOCDMF \ + -DDEV -D_THREAD_SAFE -DSHALLOW=0 -DEPSWTOK=1 -DLITE=0 \ -DNOMD2 -DNORIPE -fPIC -DDEFENSIVE_MECHLIST \ -DTOK_NEW_DATA_STORE=0x0003000c \ -DSTDLL_NAME=\"ep11tok\" \ -I${srcdir}/usr/lib/ep11_stdll -I${srcdir}/usr/lib/common \ -I${srcdir}/usr/include -I${top_builddir}/usr/lib/api \ - -I${srcdir}/usr/lib/api + -I${srcdir}/usr/lib/api -I${top_builddir}/usr/lib/config \ + -I${srcdir}/usr/lib/config opencryptoki_stdll_libpkcs11_ep11_la_LDFLAGS = \ -shared -Wl,-z,defs,-Bsymbolic -lc -lpthread -lcrypto -lrt \ @@ -38,10 +39,12 @@ usr/lib/common/shared_memory.c usr/lib/common/attributes.c \ usr/lib/common/sw_crypt.c usr/lib/common/profile_obj.c \ usr/lib/common/dlist.c usr/lib/common/pkey_utils.c \ - usr/lib/ep11_stdll/new_host.c \ + usr/lib/ep11_stdll/new_host.c usr/lib/common/mech_openssl.c \ usr/lib/ep11_stdll/ep11_specific.c \ usr/lib/common/utility_common.c usr/lib/common/ec_supported.c \ - usr/lib/api/policyhelper.c + usr/lib/api/policyhelper.c usr/lib/config/configuration.c \ + usr/lib/config/cfgparse.y usr/lib/config/cfglex.l \ + usr/lib/common/pqc_supported.c if ENABLE_LOCKS opencryptoki_stdll_libpkcs11_ep11_la_SOURCES += \ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11tok.conf opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11tok.conf --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/ep11tok.conf 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/ep11tok.conf 2023-02-13 09:22:42.000000000 +0100 @@ -2,13 +2,19 @@ # EP11 token configuration # # In order to use the EP11 Token you need to specify a list of -# adapter/domain pairs installed and configured on your system. +# adapter/domain pairs installed and configured on your system using +# the APQN_ALLOWLIST or APQN_ANY keywords, see below. All other +# settings are optional. +# +# -------------------------------------------------------------------------- # # To force that the default for CKA_SENSITIVE is CK_TRUE for # secret keys specify the following option: # # FORCE_SENSITIVE # +# -------------------------------------------------------------------------- +# # To enable strict-mode, specify the following option: # # STRICT_MODE @@ -17,12 +23,16 @@ # session that created it. When the PKCS#11 session ends, all session # keys created for this session can no longer be used. # -# VHSM_MODE +# -------------------------------------------------------------------------- # # In VHSM-mode (virtual-HSM), all keys generated by the EP-11 token will # strictly belong to the EP11 token that created it. Every EP11 token # requires a VHSM-pin to be set using the pkcsep11_session tool. # +# VHSM_MODE +# +# -------------------------------------------------------------------------- +# # The list of mechanisms returned by C_GetMechanismList is filtered # using the control point settings of the used crypto adapters. # The EP11 CP-filter config file is used to associate certain @@ -34,11 +44,15 @@ # # CPFILTER /etc/opencryptoki/ep11cpfilter.conf # +# -------------------------------------------------------------------------- +# # To enable optimization of single part Sign/Verify and Encrypt/Decrypt # operations specify the following option: # # OPTIMIZE_SINGLE_PART_OPERATIONS # +# -------------------------------------------------------------------------- +# # To optimize digest operations using CPACF the libica library is used. # Use the DIGEST_LIBICA option to control which libica library is loaded. # Specify the path of the libica library to use a specific libica library, @@ -47,12 +61,16 @@ # # DIGEST_LIBICA | DEFAULT | OFF # +# -------------------------------------------------------------------------- +# # By default the random number generator of the EP11 cypto adatper is used to # generate random data. Specify the USE_PRANDOM option to read random data from # /dev/prandom instead (or /dev/urandom if /dev/prandom is not available). # # USE_PRANDOM # +# -------------------------------------------------------------------------- +# # To optimize encrypt/decrypt and sign/verify performance, a corresponding # protected key can be created for AES secure keys and added to the secure key. # This protected key is then used for certain mechanisms via CPACF, instead of @@ -76,7 +94,22 @@ # ENABLE4NONEXTR : If the application specified CKA_EXTRACTABLE=false, # but not CKA_IBM_PROTKEY_EXTRACTABLE, new keys get # CKA_IBM_PROTKEY_EXTRACTABLE=true internally. +# +# -------------------------------------------------------------------------- # +# Specify the expected wrapping key verification pattern. When specified, all +# APQNs configured for the token must have been set up with this wrapping key +# verification pattern. +# You can use the TKE or ep11info to query the current wrapping key verification +# pattern of an APQN: +# ep11info -m -d -D +# You can also find the wrapping key verification pattern for EP11 APQNs +# in sysfs: 'cat /sys/bus/ap/devices/./mkvps' +# +# EXPECTED_WKVP "" +# +# -------------------------------------------------------------------------- +# # There are 2 ways to specify the crypto adapters: # 1) explicitly list of adapter/domain pairs # diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/new_host.c opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/new_host.c --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/new_host.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/new_host.c 2023-02-13 09:22:42.000000000 +0100 @@ -482,7 +482,7 @@ CK_RV rc = CKR_OK; TOKEN_DATA_VERSION *dat; unsigned char login_key[32], wrap_key[32], login_salt[64], wrap_salt[64]; - uint64_t login_it, wrap_it; + uint64_t login_it = 0, wrap_it = 0; if (tokdata->initialized == FALSE) { TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); @@ -1150,7 +1150,7 @@ goto done; } - rc = session_mgr_get_op_state(sess, length_only, pOperationState, + rc = session_mgr_get_op_state(tokdata, sess, length_only, pOperationState, pulOperationStateLen); if (rc != CKR_OK) TRACE_DEVEL("session_mgr_get_op_state() failed.\n"); @@ -1212,6 +1212,35 @@ return rc; } +CK_RV SC_SessionCancel(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, + CK_FLAGS flags) +{ + SESSION *sess = NULL; + CK_RV rc = CKR_OK; + + if (tokdata->initialized == FALSE) { + TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); + rc = CKR_CRYPTOKI_NOT_INITIALIZED; + goto done; + } + + sess = session_mgr_find(tokdata, sSession->sessionh); + if (!sess) { + TRACE_ERROR("%s\n", ock_err(ERR_SESSION_HANDLE_INVALID)); + rc = CKR_SESSION_HANDLE_INVALID; + goto done; + } + + rc = session_mgr_cancel(tokdata, sess, flags); + +done: + TRACE_INFO("SC_SessionCancel: sess = %lu\n", sSession->sessionh); + + if (sess != NULL) + session_mgr_put(tokdata, sess); + + return rc; +} CK_RV SC_Login(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, CK_USER_TYPE userType, CK_CHAR_PTR pPin, CK_ULONG ulPinLen) @@ -1743,7 +1772,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); if (rc == CKR_OK && attr->ulValueLen != CK_UNAVAILABLE_INFORMATION) { @@ -1801,7 +1830,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -1866,7 +1895,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -2032,13 +2061,19 @@ sess->encr_ctx.multi_init = FALSE; sess->encr_ctx.multi = FALSE; - if (ep11tok_optimize_single_ops(tokdata) && + if ((ep11tok_optimize_single_ops(tokdata) || + ep11tok_mech_single_only(pMechanism)) && !ep11tok_pkey_usage_ok(tokdata, sess, hKey, pMechanism)) { /* In case of a single part encrypt operation we don't need the * EncryptInit, instead we can use the EncryptSingle which is much * faster. In case of multi-part operations we are doing the EncryptInit * when EncryptUpdate comes into play. */ + rc = ep11tok_check_single_mech_key(tokdata, sess, pMechanism, hKey, + OP_ENCRYPT_INIT); + if (rc != CKR_OK) + goto done; + sess->encr_ctx.init_pending = TRUE; sess->encr_ctx.active = TRUE; sess->encr_ctx.key = hKey; @@ -2053,6 +2088,7 @@ } else { TRACE_ERROR("%s Memory allocation failed\n", __func__); rc = CKR_HOST_MEMORY; + encr_mgr_cleanup(tokdata, sess, &sess->encr_ctx); goto done; } } else { @@ -2124,7 +2160,8 @@ goto done; } - if (ep11tok_optimize_single_ops(tokdata) && + if ((ep11tok_optimize_single_ops(tokdata) || + ep11tok_mech_single_only(&sess->encr_ctx.mech)) && !ep11tok_pkey_usage_ok(tokdata, sess, sess->encr_ctx.key, &sess->encr_ctx.mech)) { rc = ep11tok_encrypt_single(tokdata, sess, &sess->encr_ctx.mech, length_only, sess->encr_ctx.key, @@ -2182,7 +2219,8 @@ goto done; } - if (sess->encr_ctx.active == FALSE) { + if (sess->encr_ctx.active == FALSE || + ep11tok_mech_single_only(&sess->encr_ctx.mech)) { TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_NOT_INITIALIZED)); rc = CKR_OPERATION_NOT_INITIALIZED; goto done; @@ -2258,7 +2296,8 @@ goto done; } - if (sess->encr_ctx.active == FALSE) { + if (sess->encr_ctx.active == FALSE || + ep11tok_mech_single_only(&sess->encr_ctx.mech)) { TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_NOT_INITIALIZED)); rc = CKR_OPERATION_NOT_INITIALIZED; goto done; @@ -2350,13 +2389,19 @@ sess->decr_ctx.multi_init = FALSE; sess->decr_ctx.multi = FALSE; - if (ep11tok_optimize_single_ops(tokdata) && + if ((ep11tok_optimize_single_ops(tokdata) || + ep11tok_mech_single_only(pMechanism)) && !ep11tok_pkey_usage_ok(tokdata, sess, hKey, pMechanism)) { /* In case of a single part decrypt operation we don't need the * DecryptInit, instead we can use the EncryptSingle which is much * faster. In case of multi-part operations we are doing the DecryptInit * when DecryptUpdate comes into play. */ + rc = ep11tok_check_single_mech_key(tokdata, sess, pMechanism, hKey, + OP_DECRYPT_INIT); + if (rc != CKR_OK) + goto done; + sess->decr_ctx.init_pending = TRUE; sess->decr_ctx.active = TRUE; sess->decr_ctx.key = hKey; @@ -2371,6 +2416,7 @@ } else { TRACE_ERROR("%s Memory allocation failed\n", __func__); rc = CKR_HOST_MEMORY; + decr_mgr_cleanup(tokdata, sess, &sess->decr_ctx); goto done; } } else { @@ -2442,7 +2488,8 @@ goto done; } - if (ep11tok_optimize_single_ops(tokdata) && + if ((ep11tok_optimize_single_ops(tokdata) || + ep11tok_mech_single_only(&sess->decr_ctx.mech)) && !ep11tok_pkey_usage_ok(tokdata, sess, sess->decr_ctx.key, &sess->decr_ctx.mech)) { rc = ep11tok_decrypt_single(tokdata, sess, &sess->decr_ctx.mech, length_only, sess->decr_ctx.key, @@ -2500,7 +2547,8 @@ goto done; } - if (sess->decr_ctx.active == FALSE) { + if (sess->decr_ctx.active == FALSE || + ep11tok_mech_single_only(&sess->decr_ctx.mech)) { TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_NOT_INITIALIZED)); rc = CKR_OPERATION_NOT_INITIALIZED; goto done; @@ -2576,7 +2624,8 @@ goto done; } - if (sess->decr_ctx.active == FALSE) { + if (sess->decr_ctx.active == FALSE || + ep11tok_mech_single_only(&sess->decr_ctx.mech)) { TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_NOT_INITIALIZED)); rc = CKR_OPERATION_NOT_INITIALIZED; goto done; @@ -2894,13 +2943,19 @@ sess->sign_ctx.multi_init = FALSE; sess->sign_ctx.multi = FALSE; - if (ep11tok_optimize_single_ops(tokdata) && + if ((ep11tok_optimize_single_ops(tokdata) || + ep11tok_mech_single_only(pMechanism)) && !ep11tok_pkey_usage_ok(tokdata, sess, hKey, pMechanism)) { /* In case of a single part sign operation we don't need the SignInit, * instead we can use the SignSingle which is much faster. * In case of multi-part operations we are doing the SignInit when * SignUpdate comes into play. */ + rc = ep11tok_check_single_mech_key(tokdata, sess, pMechanism, hKey, + OP_SIGN_INIT); + if (rc != CKR_OK) + goto done; + sess->sign_ctx.init_pending = TRUE; sess->sign_ctx.active = TRUE; sess->sign_ctx.key = hKey; @@ -2915,6 +2970,7 @@ } else { TRACE_ERROR("%s Memory allocation failed\n", __func__); rc = CKR_HOST_MEMORY; + sign_mgr_cleanup(tokdata, sess, &sess->sign_ctx); goto done; } } else { @@ -2996,7 +3052,8 @@ goto done; } - if (ep11tok_optimize_single_ops(tokdata) && + if ((ep11tok_optimize_single_ops(tokdata) || + ep11tok_mech_single_only(&sess->sign_ctx.mech)) && !ep11tok_pkey_usage_ok(tokdata, sess, sess->sign_ctx.key, &sess->sign_ctx.mech)) { rc = ep11tok_sign_single(tokdata, sess, &sess->sign_ctx.mech, length_only, sess->sign_ctx.key, @@ -3051,7 +3108,8 @@ goto done; } - if (sess->sign_ctx.active == FALSE) { + if (sess->sign_ctx.active == FALSE || + ep11tok_mech_single_only(&sess->sign_ctx.mech)) { TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_NOT_INITIALIZED)); rc = CKR_OPERATION_NOT_INITIALIZED; goto done; @@ -3133,7 +3191,8 @@ goto done; } - if (sess->sign_ctx.active == FALSE) { + if (sess->sign_ctx.active == FALSE || + ep11tok_mech_single_only(&sess->sign_ctx.mech)) { TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_NOT_INITIALIZED)); rc = CKR_OPERATION_NOT_INITIALIZED; goto done; @@ -3283,13 +3342,19 @@ sess->verify_ctx.multi_init = FALSE; sess->verify_ctx.multi = FALSE; - if (ep11tok_optimize_single_ops(tokdata) && + if ((ep11tok_optimize_single_ops(tokdata) || + ep11tok_mech_single_only(pMechanism)) && !ep11tok_pkey_usage_ok(tokdata, sess, hKey, pMechanism)) { /* In case of a single part verify operation we don't need the * VerifyInit, instead we can use the VerifySingle which is much * faster. In case of multi-part operations we are doing the VerifyInit * when VerifyUpdate comes into play. */ + rc = ep11tok_check_single_mech_key(tokdata, sess, pMechanism, hKey, + OP_VERIFY_INIT); + if (rc != CKR_OK) + goto done; + sess->verify_ctx.init_pending = TRUE; sess->verify_ctx.active = TRUE; sess->verify_ctx.multi = FALSE; @@ -3305,6 +3370,7 @@ } else { TRACE_ERROR("%s Memory allocation failed\n", __func__); rc = CKR_HOST_MEMORY; + verify_mgr_cleanup(tokdata, sess, &sess->verify_ctx); goto done; } } else { @@ -3382,7 +3448,8 @@ goto done; } - if (ep11tok_optimize_single_ops(tokdata) && + if ((ep11tok_optimize_single_ops(tokdata) || + ep11tok_mech_single_only(&sess->verify_ctx.mech)) && !ep11tok_pkey_usage_ok(tokdata, sess, sess->verify_ctx.key, &sess->verify_ctx.mech)) { rc = ep11tok_verify_single(tokdata, sess, &sess->verify_ctx.mech, sess->verify_ctx.key, pData, ulDataLen, @@ -3435,7 +3502,8 @@ goto done; } - if (sess->verify_ctx.active == FALSE) { + if (sess->verify_ctx.active == FALSE || + ep11tok_mech_single_only(&sess->verify_ctx.mech)) { rc = CKR_OPERATION_NOT_INITIALIZED; TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_NOT_INITIALIZED)); goto done; @@ -3516,7 +3584,8 @@ goto done; } - if (sess->verify_ctx.active == FALSE) { + if (sess->verify_ctx.active == FALSE || + ep11tok_mech_single_only(&sess->verify_ctx.mech)) { rc = CKR_OPERATION_NOT_INITIALIZED; TRACE_ERROR("%s\n", ock_err(ERR_OPERATION_NOT_INITIALIZED)); goto done; @@ -3611,20 +3680,17 @@ CK_ULONG ulPartLen, CK_BYTE_PTR pEncryptedPart, CK_ULONG_PTR pulEncryptedPartLen) { - UNUSED(sSession); - UNUSED(pPart); - UNUSED(ulPartLen); - UNUSED(pEncryptedPart); - UNUSED(pulEncryptedPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_EncryptUpdate(tokdata, sSession, pPart, ulPartLen, + pEncryptedPart, pulEncryptedPartLen); + if (rc != CKR_OK || pEncryptedPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_DigestUpdate(tokdata, sSession, pPart, ulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -3634,20 +3700,17 @@ CK_ULONG ulEncryptedPartLen, CK_BYTE_PTR pPart, CK_ULONG_PTR pulPartLen) { - UNUSED(sSession); - UNUSED(pEncryptedPart); - UNUSED(ulEncryptedPartLen); - UNUSED(pPart); - UNUSED(pulPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_DecryptUpdate(tokdata, sSession, pEncryptedPart, + ulEncryptedPartLen, pPart, pulPartLen); + if (rc != CKR_OK || pPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_DigestUpdate(tokdata, sSession, pPart, *pulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -3656,43 +3719,36 @@ CK_ULONG ulPartLen, CK_BYTE_PTR pEncryptedPart, CK_ULONG_PTR pulEncryptedPartLen) { - UNUSED(sSession); - UNUSED(pPart); - UNUSED(ulPartLen); - UNUSED(pEncryptedPart); - UNUSED(pulEncryptedPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_EncryptUpdate(tokdata, sSession, pPart, ulPartLen, + pEncryptedPart, pulEncryptedPartLen); + if (rc != CKR_OK || pEncryptedPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_SignUpdate(tokdata, sSession, pPart, ulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } - CK_RV SC_DecryptVerifyUpdate(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, CK_BYTE_PTR pEncryptedPart, CK_ULONG ulEncryptedPartLen, CK_BYTE_PTR pPart, CK_ULONG_PTR pulPartLen) { - UNUSED(sSession); - UNUSED(pEncryptedPart); - UNUSED(ulEncryptedPartLen); - UNUSED(pPart); - UNUSED(pulPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_DecryptUpdate(tokdata, sSession, pEncryptedPart, + ulEncryptedPartLen, pPart, pulPartLen); + if (rc != CKR_OK || pPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_VerifyUpdate(tokdata, sSession, pPart, *pulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -3758,7 +3814,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -3855,13 +3911,13 @@ TRACE_DEBUG("Public Template:\n"); attr = pPublicKeyTemplate; - for (i = 0; i < ulPublicKeyAttributeCount; i++, attr++) { + for (i = 0; i < ulPublicKeyAttributeCount && attr != NULL; i++, attr++) { TRACE_DEBUG_DUMPATTR(attr); } TRACE_DEBUG("Private Template:\n"); attr = pPrivateKeyTemplate; - for (i = 0; i < ulPrivateKeyAttributeCount; i++, attr++) { + for (i = 0; i < ulPrivateKeyAttributeCount && attr != NULL; i++, attr++) { TRACE_DEBUG_DUMPATTR(attr); } #endif @@ -3986,7 +4042,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -4090,7 +4146,7 @@ } attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -4150,6 +4206,9 @@ goto done; } + if (ulRandomLen == 0) + goto done; + rc = rng_generate(tokdata, pRandomData, ulRandomLen); if (rc != CKR_OK) TRACE_DEVEL("rng_generate() failed.\n"); @@ -4233,6 +4292,13 @@ if (rc != CKR_OK) goto done; + if (pDecrMech->mechanism == CKM_AES_XTS || + pEncrMech->mechanism == CKM_AES_XTS) { + TRACE_ERROR("IBM_ReencryptSingle with AES-XTS is not supported\n"); + rc = CKR_MECHANISM_INVALID; + goto done; + } + if (pin_expired(&sess->session_info, tokdata->nv_token_data->token_info.flags) == TRUE) { TRACE_ERROR("%s\n", ock_err(ERR_PIN_EXPIRED)); @@ -4336,10 +4402,10 @@ function_list.ST_VerifyFinal = SC_VerifyFinal; function_list.ST_VerifyRecoverInit = SC_VerifyRecoverInit; function_list.ST_VerifyRecover = SC_VerifyRecover; - function_list.ST_DigestEncryptUpdate = NULL; // SC_DigestEncryptUpdate; - function_list.ST_DecryptDigestUpdate = NULL; // SC_DecryptDigestUpdate; - function_list.ST_SignEncryptUpdate = NULL; //SC_SignEncryptUpdate; - function_list.ST_DecryptVerifyUpdate = NULL; // SC_DecryptVerifyUpdate; + function_list.ST_DigestEncryptUpdate = SC_DigestEncryptUpdate; + function_list.ST_DecryptDigestUpdate = SC_DecryptDigestUpdate; + function_list.ST_SignEncryptUpdate = SC_SignEncryptUpdate; + function_list.ST_DecryptVerifyUpdate = SC_DecryptVerifyUpdate; function_list.ST_GenerateKey = SC_GenerateKey; function_list.ST_GenerateKeyPair = SC_GenerateKeyPair; function_list.ST_WrapKey = SC_WrapKey; @@ -4349,6 +4415,7 @@ function_list.ST_GenerateRandom = SC_GenerateRandom; function_list.ST_GetFunctionStatus = NULL; // SC_GetFunctionStatus; function_list.ST_CancelFunction = NULL; // SC_CancelFunction; + function_list.ST_SessionCancel = SC_SessionCancel; function_list.ST_IBM_ReencryptSingle = SC_IBM_ReencryptSingle; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/tok_struct.h opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/tok_struct.h --- opencryptoki-3.18.0+dfsg/usr/lib/ep11_stdll/tok_struct.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ep11_stdll/tok_struct.h 2023-02-13 09:22:42.000000000 +0100 @@ -114,6 +114,7 @@ NULL, // generic_secret_key_gen // AES NULL, // aes_key_gen, + NULL, // aes_xts_key_gen &token_specific_aes_ecb, &token_specific_aes_cbc, NULL, // aes_ctr @@ -125,6 +126,7 @@ NULL, // aes_cfb NULL, // aes_mac &token_specific_aes_cmac, + &token_specific_aes_xts, // aes_xts // DSA NULL, // dsa_generate_keypair, NULL, // dsa_sign diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ica_s390_stdll/ica_s390_stdll.mk opencryptoki-3.20.0+dfsg/usr/lib/ica_s390_stdll/ica_s390_stdll.mk --- opencryptoki-3.18.0+dfsg/usr/lib/ica_s390_stdll/ica_s390_stdll.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ica_s390_stdll/ica_s390_stdll.mk 2023-02-13 09:22:42.000000000 +0100 @@ -4,7 +4,7 @@ opencryptoki_stdll_libpkcs11_ica_la_CFLAGS = \ -DDEV -D_THREAD_SAFE -fPIC -DSHALLOW=0 -DSWTOK=0 -DLITE=1 \ - -DNODH -DNOCDMF -DNOMD2 -DNODSA -DSTDLL_NAME=\"icatok\" \ + -DNODH -DNOMD2 -DNODSA -DSTDLL_NAME=\"icatok\" \ -DTOK_NEW_DATA_STORE=0x0003000c \ $(ICA_INC_DIRS) -I${srcdir}/usr/lib/ica_s390_stdll \ -I${srcdir}/usr/lib/common -I${srcdir}/usr/include \ @@ -13,7 +13,7 @@ opencryptoki_stdll_libpkcs11_ica_la_LDFLAGS = \ $(LCRYPTO) $(ICA_LIB_DIRS) -nostartfiles -shared \ -Wl,-z,defs,-Bsymbolic -Wl,-soname,$@ -lc -lpthread -lica -ldl \ - -lcrypto -lrt \ + -lcrypto -lrt -llber \ -Wl,--version-script=${srcdir}/opencryptoki_tok.map opencryptoki_stdll_libpkcs11_ica_la_SOURCES = \ @@ -38,7 +38,7 @@ usr/lib/ica_s390_stdll/ica_specific.c usr/lib/common/dlist.c \ usr/lib/common/mech_openssl.c \ usr/lib/common/utility_common.c usr/lib/common/ec_supported.c \ - usr/lib/api/policyhelper.c + usr/lib/api/policyhelper.c usr/lib/common/pqc_supported.c if ENABLE_LOCKS opencryptoki_stdll_libpkcs11_ica_la_SOURCES += \ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ica_s390_stdll/ica_specific.c opencryptoki-3.20.0+dfsg/usr/lib/ica_s390_stdll/ica_specific.c --- opencryptoki-3.18.0+dfsg/usr/lib/ica_s390_stdll/ica_specific.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ica_s390_stdll/ica_specific.c 2023-02-13 09:22:42.000000000 +0100 @@ -10,16 +10,17 @@ /* Modified for S390 by Robert Burroughs */ +#define _GNU_SOURCE + #include #include // for memcmp() et al #include #include #include // for dlopen() +#include #include -#ifndef NOAES #include -#endif #include "pkcs11types.h" #include "p11util.h" @@ -84,8 +85,6 @@ static pthread_mutex_t rngmtx = PTHREAD_MUTEX_INITIALIZER; -#define LIBICA_SHARED_LIB_V3 "libica.so.3" -#define LIBICA_SHARED_LIB_V4 "libica.so.4" #define BIND(dso, sym) do { \ if (p_##sym == NULL) \ *(void **)(&p_##sym) = dlsym(dso, #sym); \ @@ -126,6 +125,16 @@ #endif typedef void (*ica_cleanup_t) (void); +typedef unsigned int (*ica_aes_xts_ex_t)(const unsigned char *in_data, + unsigned char *out_data, + unsigned long data_length, + unsigned char *key1, + unsigned char *key2, + unsigned int key_length, + unsigned char *tweak, + unsigned char *iv, + unsigned int direction); + /* * These symbols loaded from libica via dlsym() can be static, even if * multiple instances of the ICA token are used. The libica library loaded @@ -147,6 +156,7 @@ static ica_ec_key_free_t p_ica_ec_key_free; #endif static ica_cleanup_t p_ica_cleanup; +static ica_aes_xts_ex_t p_ica_aes_xts_ex; static CK_RV mech_list_ica_initialize(STDLL_TokData_t *tokdata); @@ -233,19 +243,48 @@ static ica_sha3_512_t p_ica_sha3_512; #endif +struct phdr_cb_data { + void *handle; +}; + +static int phdr_callback(struct dl_phdr_info *info, size_t size, void *data) +{ + int j; + unsigned long start, end; + struct phdr_cb_data *d = data; + unsigned long myaddr = (unsigned long)&ica_open_adapter; + + UNUSED(size); + + for (j = 0; j < info->dlpi_phnum; j++) { + /* Only consider loadable program segments */ + if (info->dlpi_phdr[j].p_type == PT_LOAD) { + start = info->dlpi_addr + info->dlpi_phdr[j].p_vaddr; + end = start + info->dlpi_phdr[j].p_memsz; + + if (start <= myaddr && myaddr < end) { + /* Get library handle of already loaded libica */ + d->handle = dlopen(info->dlpi_name, RTLD_NOW | RTLD_NOLOAD); + break; + } + } + } + return 0; +} + static CK_RV load_libica(ica_private_data_t *ica_data) { - /* Load libica */ - ica_data->libica_dso = dlopen(LIBICA_SHARED_LIB_V4, RTLD_NOW); - if (ica_data->libica_dso == NULL) - ica_data->libica_dso = dlopen(LIBICA_SHARED_LIB_V3, RTLD_NOW); - - if (ica_data->libica_dso == NULL) { - TRACE_ERROR("%s: dlopen(%s or %s) failed: %s\n", __func__, - LIBICA_SHARED_LIB_V4, LIBICA_SHARED_LIB_V3, dlerror()); + struct phdr_cb_data data = { .handle = NULL }; + + /* Find already loaded libica that it was linked with */ + dl_iterate_phdr(phdr_callback, &data); + if (data.handle == NULL) { + TRACE_ERROR("%s: Failed to find libica: %s\n", __func__, dlerror()); return CKR_FUNCTION_FAILED; } + ica_data->libica_dso = data.handle; + #ifndef NO_EC /* Try to resolve all needed functions for ecc support */ BIND(ica_data->libica_dso, ica_ec_key_new); @@ -280,6 +319,8 @@ BIND(ica_data->libica_dso, ica_cleanup); + BIND(ica_data->libica_dso, ica_aes_xts_ex); + return CKR_OK; } @@ -364,8 +405,6 @@ { ica_private_data_t *ica_data = (ica_private_data_t *)tokdata->private_data; - UNUSED(in_fork_initializer); - TRACE_INFO("ica %s running\n", __func__); ica_close_adapter(ica_data->adapter_handle); @@ -1824,6 +1863,7 @@ CK_RV rc; ica_rsa_key_mod_expo_t *publKey = NULL; ica_rsa_key_crt_t *privKey = NULL; + unsigned int try = 0; rc = template_attribute_get_ulong(publ_tmpl, CKA_MODULUS_BITS, &mod_bits); if (rc != CKR_OK) { @@ -1895,7 +1935,8 @@ ptr = publKey->exponent + publKey->key_length - sizeof(unsigned long); if (*((unsigned long *) ptr) != 0 && *((unsigned long *) ptr) % 2 == 0) { TRACE_ERROR("%s\n", ock_err(ERR_TEMPLATE_INCONSISTENT)); - return CKR_TEMPLATE_INCONSISTENT; + rc = CKR_TEMPLATE_INCONSISTENT; + goto pubkey_cleanup; } @@ -1949,6 +1990,8 @@ goto privkey_cleanup; } +retry: + try++; rc = ica_rsa_key_generate_crt(ica_data->adapter_handle, (unsigned int) mod_bits, publKey, privKey); switch (rc) { @@ -1971,8 +2014,10 @@ goto privkey_cleanup; break; default: - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); + TRACE_ERROR("%s (try %u)\n", ock_err(ERR_FUNCTION_FAILED), try); rc = CKR_FUNCTION_FAILED; + if (try <= 10) + goto retry; goto privkey_cleanup; break; } @@ -2606,8 +2651,6 @@ os_specific_rsa_decrypt); } -#ifndef NOAES - CK_RV token_specific_aes_key_gen(STDLL_TokData_t *tokdata, CK_BYTE **key, CK_ULONG *len, CK_ULONG keysize, CK_BBOOL *is_opaque) @@ -2621,6 +2664,19 @@ return rng_generate(tokdata, *key, keysize); } +CK_RV token_specific_aes_xts_key_gen(STDLL_TokData_t *tokdata, CK_BYTE **key, + CK_ULONG *len, CK_ULONG keysize, + CK_BBOOL *is_opaque) +{ + *key = malloc(keysize); + if (*key == NULL) + return CKR_HOST_MEMORY; + *len = keysize; + *is_opaque = FALSE; + + return rng_generate(tokdata, *key, keysize); +} + CK_RV token_specific_aes_ecb(STDLL_TokData_t *tokdata, CK_BYTE *in_data, CK_ULONG in_data_len, CK_BYTE *out_data, CK_ULONG *out_data_len, @@ -3037,8 +3093,8 @@ context->len = remain; } else { /* case 2 - partial data */ memcpy(buffer, context->data, AES_BLOCK_SIZE); - memcpy(context->data, context->data + AES_BLOCK_SIZE, - context->len - AES_BLOCK_SIZE); + memmove(context->data, context->data + AES_BLOCK_SIZE, + context->len - AES_BLOCK_SIZE); memcpy(context->data + context->len - AES_BLOCK_SIZE, in_data, in_data_len); context->len = context->len - AES_BLOCK_SIZE + in_data_len; @@ -3400,7 +3456,62 @@ return rc; } -#endif +CK_RV token_specific_aes_xts(STDLL_TokData_t *tokdata, + CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len, + OBJECT *key_obj, CK_BYTE *tweak, + CK_BOOL encrypt, CK_BBOOL initial, CK_BBOOL final, + CK_BYTE* iv) +{ + ica_private_data_t *ica_data = (ica_private_data_t *)tokdata->private_data; + CK_ATTRIBUTE *key_attr; + CK_RV rc; + + UNUSED(tokdata); + + if (!ica_data->ica_aes_available || p_ica_aes_xts_ex == NULL) + return openssl_specific_aes_xts(tokdata, in_data, in_data_len, + out_data, out_data_len, key_obj, + tweak, encrypt, initial, final, iv); + + /* Full block size unless final call */ + if (!final && (in_data_len % AES_BLOCK_SIZE) != 0) + return CKR_DATA_LEN_RANGE; + /* Final block must be at least one full block */ + if (final && in_data_len < AES_BLOCK_SIZE) + return CKR_DATA_LEN_RANGE; + + if (out_data == NULL) { + *out_data_len = in_data_len; + return CKR_OK; + } + + if (*out_data_len < in_data_len) + return CKR_BUFFER_TOO_SMALL; + + rc = template_attribute_get_non_empty(key_obj->template, CKA_VALUE, + &key_attr); + if (rc != CKR_OK) { + TRACE_ERROR("Could not find CKA_VALUE for the key.\n"); + return rc; + } + + rc = p_ica_aes_xts_ex(in_data, out_data, in_data_len, + key_attr->pValue, (unsigned char *)key_attr->pValue + + key_attr->ulValueLen / 2, + key_attr->ulValueLen / 2, + initial ? tweak : NULL, iv, + encrypt ? ICA_ENCRYPT : ICA_DECRYPT); + + if (rc == 0) { + *out_data_len = in_data_len; + } else { + TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_FAILED)); + rc = CKR_FUNCTION_FAILED; + } + + return rc; +} typedef struct _REF_MECH_LIST_ELEMENT { CK_ULONG lica_idx; /* 0 means its a combined mechanism */ @@ -3509,8 +3620,8 @@ {54, CKM_MD5_HMAC, {0, 0, CKF_SIGN | CKF_VERIFY}}, {55, CKM_MD5_HMAC_GENERAL, {0, 0, CKF_SIGN | CKF_VERIFY}}, #endif -#if !(NOAES) {P_RNG, CKM_AES_KEY_GEN, {16, 32, CKF_GENERATE}}, + {P_RNG, CKM_AES_XTS_KEY_GEN, {32, 64, CKF_GENERATE}}, {AES_ECB, CKM_AES_ECB, {16, 32, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP} }, @@ -3540,7 +3651,9 @@ {AES_CMAC, CKM_AES_MAC_GENERAL, {16, 32, CKF_SIGN | CKF_VERIFY}}, {AES_CMAC, CKM_AES_CMAC, {16, 32, CKF_SIGN | CKF_VERIFY}}, {AES_CMAC, CKM_AES_CMAC_GENERAL, {16, 32, CKF_SIGN | CKF_VERIFY}}, -#endif + {AES_XTS, CKM_AES_XTS, + {32, 64, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP} + }, {P_RNG, CKM_GENERIC_SECRET_KEY_GEN, {80, 2048, CKF_GENERATE}}, #ifndef NO_EC {EC_DH, CKM_ECDH1_DERIVE, @@ -3919,7 +4032,7 @@ ica_data->mech_list[ica_data->mech_list_len].mech_type = ref_mech_list[refIdx].mech_type; ica_data->mech_list[ica_data->mech_list_len].mech_info.flags = - (libica_func_list[i].flags & (ICA_FLAG_DHW | ICA_FLAG_SHW) ? CKF_HW : 0) | + ((libica_func_list[i].flags & (ICA_FLAG_DHW | ICA_FLAG_SHW)) ? CKF_HW : 0) | (ref_mech_list[refIdx].mech_info.flags & (~CKF_HW)); ica_data->mech_list[ica_data->mech_list_len].mech_info.ulMinKeySize = ref_mech_list[refIdx].mech_info.ulMinKeySize; @@ -3930,18 +4043,24 @@ libica_func_list[i].mech_mode_id == RSA_ME) adjust_rsa_key_sizes(rsa_props, &ica_data->mech_list[ica_data->mech_list_len].mech_info); + if (libica_func_list[i].mech_mode_id == AES_XTS && + p_ica_aes_xts_ex == NULL) + ica_data->mech_list[ica_data->mech_list_len].mech_info.flags &= (~CKF_HW); ica_data->mech_list_len++; } else { /* replace existing entry */ ica_data->mech_list[ulActMechCtr].mech_info.flags = - (libica_func_list[i].flags & (ICA_FLAG_DHW | ICA_FLAG_SHW) ? CKF_HW : 0) | + ((libica_func_list[i].flags & (ICA_FLAG_DHW | ICA_FLAG_SHW)) ? CKF_HW : 0) | (ref_mech_list[refIdx].mech_info.flags & (~CKF_HW)); if (libica_func_list[i].mech_mode_id == RSA_KEY_GEN_ME || libica_func_list[i].mech_mode_id == RSA_ME) adjust_rsa_key_sizes(rsa_props, &ica_data->mech_list[ulActMechCtr].mech_info); + if (libica_func_list[i].mech_mode_id == AES_XTS && + p_ica_aes_xts_ex == NULL) + ica_data->mech_list[ulActMechCtr].mech_info.flags &= (~CKF_HW); } refIdx++; } @@ -3981,9 +4100,11 @@ if (isMechanismAvailable(tokdata, CKM_SHA512) && isMechanismAvailable(tokdata, CKM_RSA_PKCS)) addMechanismToList(tokdata, CKM_SHA512_RSA_PKCS, rsa_hw && sha_hw, rsa_props); +#if !(NOMD2 ) if (isMechanismAvailable(tokdata, CKM_MD2) && isMechanismAvailable(tokdata, CKM_RSA_PKCS)) addMechanismToList(tokdata, CKM_MD2_RSA_PKCS, rsa_hw && sha_hw, rsa_props); +#endif if (isMechanismAvailable(tokdata, CKM_MD5) && isMechanismAvailable(tokdata, CKM_RSA_PKCS)) addMechanismToList(tokdata, CKM_MD5_RSA_PKCS, rsa_hw && sha_hw, rsa_props); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/ica_s390_stdll/tok_struct.h opencryptoki-3.20.0+dfsg/usr/lib/ica_s390_stdll/tok_struct.h --- opencryptoki-3.18.0+dfsg/usr/lib/ica_s390_stdll/tok_struct.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/ica_s390_stdll/tok_struct.h 2023-02-13 09:22:42.000000000 +0100 @@ -108,8 +108,8 @@ NULL, // hmac_verify_final &token_specific_generic_secret_key_gen, // AES -#ifndef NOAES &token_specific_aes_key_gen, + &token_specific_aes_xts_key_gen, &token_specific_aes_ecb, &token_specific_aes_cbc, &token_specific_aes_ctr, @@ -121,20 +121,7 @@ &token_specific_aes_cfb, &token_specific_aes_mac, &token_specific_aes_cmac, -#else - NULL, // aes_key_gen, - NULL, // aes_ecb, - NULL, // aes_cbc, - NULL, // aes_ctr, - NULL, // aes_gcm_init, - NULL, // aes_gcm, - NULL, // aes_gcm_update, - NULL, // aes_gcm_final, - NULL, // aes_ofb, - NULL, // aes_cfb, - NULL, // aes_mac, - NULL, // aes_cmac -#endif + &token_specific_aes_xts, // DSA NULL, // dsa_generate_keypair NULL, // dsa_sign diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/icsf.c opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/icsf.c --- opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/icsf.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/icsf.c 2023-02-13 09:22:42.000000000 +0100 @@ -244,7 +244,7 @@ if (rc != LDAP_OPT_SUCCESS) { TRACE_ERROR("Failed to get LDAP version: %s (%d)\n", ldap_err2string(rc), rc); - return -1; + return rc; } if (version < LDAP_VERSION3) { TRACE_INFO("Changing version from %d to %d.\n", version, LDAP_VERSION3); @@ -253,7 +253,7 @@ if (rc != LDAP_OPT_SUCCESS) { TRACE_ERROR("Failed to set LDAP version: %s (%d)\n", ldap_err2string(rc), rc); - return -1; + return rc; } } @@ -282,7 +282,7 @@ if (rc != LDAP_SUCCESS) { TRACE_ERROR("Failed to connect to \"%s\": %s (%d)\n", uri ? uri : "(null)", ldap_err2string(rc), rc); - return -1; + return rc; } if (icsf_force_ldap_v3(*ld)) @@ -294,7 +294,7 @@ rc = ldap_sasl_bind_s(*ld, dn, LDAP_SASL_SIMPLE, &cred, NULL, NULL, NULL); if (rc != LDAP_SUCCESS) { TRACE_ERROR("LDAP bind failed: %s (%d)\n", ldap_err2string(rc), rc); - return -1; + return rc; } return 0; @@ -320,7 +320,7 @@ if (rc != LDAP_SUCCESS) { TRACE_ERROR("Failed to set certificate file for TLS: " "%s (%d)\n", ldap_err2string(rc), rc); - return -1; + return rc; } } @@ -330,7 +330,7 @@ if (rc != LDAP_SUCCESS) { TRACE_ERROR("Failed to set key file for TLS: " "%s (%d)\n", ldap_err2string(rc), rc); - return -1; + return rc; } } @@ -340,7 +340,7 @@ if (rc != LDAP_SUCCESS) { TRACE_ERROR("Failed to set CA certificate file for TLS:" " %s (%d)\n", ldap_err2string(rc), rc); - return -1; + return rc; } } @@ -350,7 +350,7 @@ if (rc != LDAP_SUCCESS) { TRACE_ERROR("Failed to set CA certificate dir for TLS: " "%s (%d)\n", ldap_err2string(rc), rc); - return -1; + return rc; } } @@ -377,15 +377,17 @@ if (rc != LDAP_SUCCESS) { TRACE_ERROR("Failed to connect to \"%s\": %s (%d)\n", uri ? uri : "(null)", ldap_err2string(rc), rc); - return -1; + return rc; } - if (icsf_force_ldap_v3(*ld)) - return -1; + rc = icsf_force_ldap_v3(*ld); + if (rc != 0) + return rc; /* Initialize TLS */ - if (icsf_set_sasl_params(*ld, cert, key, ca, ca_dir)) - return -1; + rc = icsf_set_sasl_params(*ld, cert, key, ca, ca_dir); + if (rc != 0) + return rc; TRACE_DEVEL("Binding\n"); rc = ldap_sasl_bind_s(*ld, NULL, "EXTERNAL", NULL, NULL, NULL, NULL); @@ -398,7 +400,7 @@ ext_msg ? ext_msg : ""); if (ext_msg) ldap_memfree(ext_msg); - return -1; + return rc; } return 0; @@ -908,6 +910,9 @@ for (i = 0; i < attrs_len; i++) { if (!is_numeric_attr(attrs[i].type)) { /* Non numeric attributes are encode as octet strings */ + if (attrs[i].type & CKA_VENDOR_DEFINED) + continue; + if (ber_printf(ber, "{ito}", attrs[i].type, 0 | LBER_CLASS_CONTEXT, attrs[i].pValue ? attrs[i].pValue : "", @@ -916,7 +921,7 @@ } } else { long value; - unsigned long mask; + unsigned long mask = 0; /* `long` is used here to support any size of integer, * however if the value is shorter than a `long` then @@ -930,7 +935,8 @@ /* Calculate a mask to get just the bits in the range of * the given length. */ - mask = (1UL << (8 * attrs[i].ulValueLen)) - 1; + if (attrs[i].ulValueLen < sizeof(long)) + mask = (1UL << (8 * attrs[i].ulValueLen)) - 1; if (mask == 0) mask = (unsigned long) -1; @@ -1574,6 +1580,8 @@ return "RSA-PKCS"; case CKM_SHA_1_HMAC: return "SHA-1"; + case CKM_SHA224_HMAC: + return "SHA-224"; case CKM_SHA256_HMAC: return "SHA-256"; case CKM_SHA384_HMAC: @@ -1591,6 +1599,11 @@ return "SHA-1 VER-RSA"; else return "SHA-1 SIGN-RSA"; + case CKM_SHA224_RSA_PKCS: + if (arg) + return "SHA-224 VER-RSA"; + else + return "SHA-224 SIGN-RSA"; case CKM_SHA256_RSA_PKCS: if (arg) return "SHA-256 VER-RSA"; @@ -1621,6 +1634,26 @@ return "SHA-1 VER-EC"; else return "SHA-1 SIGN-EC"; + case CKM_ECDSA_SHA224: + if (arg) + return "SHA-224 VER-EC"; + else + return "SHA-224 SIGN-EC"; + case CKM_ECDSA_SHA256: + if (arg) + return "SHA-256 VER-EC"; + else + return "SHA-256 SIGN-EC"; + case CKM_ECDSA_SHA384: + if (arg) + return "SHA-384 VER-EC"; + else + return "SHA-384 SIGN-EC"; + case CKM_ECDSA_SHA512: + if (arg) + return "SHA-512 VER-EC"; + else + return "SHA-512 SIGN-EC"; case CKM_SSL3_KEY_AND_MAC_DERIVE: return "SSL-KM"; case CKM_TLS_KEY_AND_MAC_DERIVE: @@ -1679,13 +1712,18 @@ block_size = MD5_BLOCK_SIZE; break; case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: block_size = SHA1_BLOCK_SIZE; break; case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: block_size = SHA384_BLOCK_SIZE; break; default: @@ -2061,7 +2099,8 @@ static int icsf_ber_decode_get_attribute_list(BerElement * berbuf, CK_ATTRIBUTE * attrs, - CK_ULONG attrs_len) + CK_ULONG attrs_len, + int *reason) { int attrtype; struct berval attrbval = { 0, NULL }; @@ -2069,7 +2108,7 @@ unsigned int i; CK_ULONG found = 0; ber_tag_t tag; - CK_RV rc = CKR_OK; + int rc = 0; if (ber_scanf(berbuf, "{{") == LBER_ERROR) goto decode_error; @@ -2116,7 +2155,8 @@ } attrs[i].ulValueLen = attrbval.bv_len; } else { - rc = CKR_BUFFER_TOO_SMALL; + rc = 8; + *reason = 3003; /* CKR_BUFFER_TOO_SMALL */ attrs[i].ulValueLen = -1; goto decode_error; } @@ -2125,6 +2165,10 @@ found++; } + if (attrbval.bv_val != NULL) + ber_memfree(attrbval.bv_val); + attrbval.bv_val = NULL; + /* if we have found all the values for our list, then * we are done. */ @@ -2137,7 +2181,8 @@ */ if (found < attrs_len) { TRACE_ERROR("%s\n", ock_err(ERR_ATTRIBUTE_TYPE_INVALID)); - rc = CKR_ATTRIBUTE_TYPE_INVALID; + rc = 8; + *reason = 3029; /* CKR_ATTRIBUTE_TYPE_INVALID */ goto decode_error; } @@ -2146,8 +2191,8 @@ decode_error: TRACE_ERROR("Failed to decode message.\n"); - if (!rc) - rc = CKR_FUNCTION_FAILED; + if (attrbval.bv_val != NULL) + ber_memfree(attrbval.bv_val); return rc; } @@ -2209,7 +2254,7 @@ * * asn.1 {{{ito|i} {ito|i} ...}i} */ - rc = icsf_ber_decode_get_attribute_list(result, attrs, attrs_len); + rc = icsf_ber_decode_get_attribute_list(result, attrs, attrs_len, reason); if (rc < 0) { TRACE_ERROR("Failed to decode message.\n"); goto cleanup; @@ -2734,6 +2779,8 @@ BerElement *result = NULL; struct berval bv_wrapped_key = { 0, NULL }; ber_int_t wrapped_key_len = 0; + ber_int_t iv_len = 0; + char *iv = ""; CHECK_ARG_NON_NULL(ld); CHECK_ARG_NON_NULL(mech); @@ -2758,6 +2805,8 @@ (unsigned long) mech->mechanism); return -1; } + iv = mech->pParameter; + iv_len = mech->ulParameterLen; break; default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_INVALID)); @@ -2788,8 +2837,10 @@ * For a size query (wrapped_key is NULL), we set wrappedKeyMaxLen to * USHRT_MAX (65535), which is hopefully large enough. */ - rc = ber_printf(msg, "ois", wrapping_handle, sizeof(wrapping_handle), - wrapped_key != NULL ? (ber_int_t)*p_wrapped_key_len : USHRT_MAX, ""); + rc = ber_printf(msg, "oio", wrapping_handle, sizeof(wrapping_handle), + wrapped_key != NULL ? + (ber_int_t)*p_wrapped_key_len : USHRT_MAX, + iv, iv_len); if (rc < 0) { rc = -1; TRACE_ERROR("Failed to encode message: %d.\n", rc); @@ -2859,6 +2910,8 @@ const char *rule_fmt = NULL; const char *rule_alg = NULL; BerElement *msg = NULL; + ber_int_t iv_len = 0; + char *iv = ""; CHECK_ARG_NON_NULL(ld); CHECK_ARG_NON_NULL(mech); @@ -2882,6 +2935,8 @@ (unsigned long) mech->mechanism); return -1; } + iv = mech->pParameter; + iv_len = mech->ulParameterLen; break; default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_INVALID)); @@ -2910,7 +2965,7 @@ * attrList Attributes * } */ - if (ber_printf(msg, "os", wrapped_key, wrapped_key_len, "") < 0 || + if (ber_printf(msg, "oo", wrapped_key, wrapped_key_len, iv, iv_len) < 0 || ber_printf(msg, "{") < 0 || icsf_ber_put_attribute_list(msg, attrs, attrs_len) || ber_printf(msg, "}") < 0) { @@ -3060,6 +3115,10 @@ 0, NULL}; struct berval publicValue = { 0, NULL }, bvParam = { 0, NULL}; + CK_ECDH1_DERIVE_PARAMS *ecdh_params = NULL; + struct berval kdfCode = { 0, NULL }; + struct berval sharedData = { 0, NULL }; + CK_BYTE kdf = 0; CHECK_ARG_NON_NULL(ld); CHECK_ARG_NON_NULL(mech); @@ -3074,6 +3133,9 @@ case CKM_DH_PKCS_DERIVE: strpad(rule_array, "PKCS-DH", ICSF_RULE_ITEM_LEN, ' '); break; + case CKM_ECDH1_DERIVE: + strpad(rule_array, "EC-DH", ICSF_RULE_ITEM_LEN, ' '); + break; default: TRACE_ERROR("%s\n", ock_err(ERR_MECHANISM_INVALID)); return -1; @@ -3102,7 +3164,11 @@ * serverRandomData OCTET STRING * } * - * EC-DH is not supported + * EC-DH_DVKInputParmsList ::= SEQUENCE { + * kdfCode OCTET STRING, + * sharedData OCTET STRING, + * EC-DH_publicValue OCTET STRING + * } * * attrList is built by icsf_ber_put_attribute_list() */ @@ -3153,6 +3219,23 @@ goto cleanup; } break; + case CKM_ECDH1_DERIVE: + ecdh_params = (CK_ECDH1_DERIVE_PARAMS *)mech->pParameter; + + kdf = ecdh_params->kdf; + kdfCode.bv_val = (char *)&kdf; + kdfCode.bv_len = sizeof(kdf); + sharedData.bv_val = (char *)ecdh_params->pSharedData; + sharedData.bv_len = ecdh_params->ulSharedDataLen; + publicValue.bv_val = (char *)ecdh_params->pPublicData; + publicValue.bv_len = ecdh_params->ulPublicDataLen; + + if (ber_printf(msg, "t{OOO}", 2 | LBER_CLASS_CONTEXT | LBER_CONSTRUCTED, + &kdfCode, &sharedData, &publicValue) < 0) { + TRACE_ERROR("Failed to encode message.\n"); + goto cleanup; + } + break; default: TRACE_ERROR("Mechanism not supported.\n"); return -1; @@ -3186,11 +3269,10 @@ version = (CK_VERSION_PTR) (¶ms->pVersion); version->major = bvParam.bv_val[0]; version->minor = bvParam.bv_val[1]; + ber_memfree(bvParam.bv_val); } } - rc = 0; - cleanup: if (msg) ber_free(msg, 1); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/icsf_specific.c opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/icsf_specific.c --- opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/icsf_specific.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/icsf_specific.c 2023-02-13 09:22:42.000000000 +0100 @@ -75,11 +75,13 @@ {512, 4096, CKF_HW | CKF_ENCRYPT | CKF_DECRYPT | CKF_SIGN | CKF_VERIFY }}, {CKM_MD5_RSA_PKCS, {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_SHA1_RSA_PKCS, {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY}}, + {CKM_SHA224_RSA_PKCS, {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_SHA256_RSA_PKCS, {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_SHA384_RSA_PKCS, {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_SHA512_RSA_PKCS, {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_SHA_1, {0, 0, CKF_HW | CKF_DIGEST}}, {CKM_SHA_1_HMAC, {0, 0, CKF_HW | CKF_SIGN | CKF_VERIFY}}, + {CKM_SHA224_HMAC, {0, 0, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_SHA256_HMAC, {0, 0, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_SHA384_HMAC, {0, 0, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_SHA512_HMAC, {0, 0, CKF_HW | CKF_SIGN | CKF_VERIFY}}, @@ -96,7 +98,19 @@ {CKM_DSA_SHA1, {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_DSA, {512, 2048, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_ECDSA_SHA1, - {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY | CKF_EC_F_P | + {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY | CKF_EC_F_P | + CKF_EC_NAMEDCURVE | CKF_EC_UNCOMPRESS}}, + {CKM_ECDSA_SHA224, + {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY | CKF_EC_F_P | + CKF_EC_NAMEDCURVE | CKF_EC_UNCOMPRESS}}, + {CKM_ECDSA_SHA256, + {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY | CKF_EC_F_P | + CKF_EC_NAMEDCURVE | CKF_EC_UNCOMPRESS}}, + {CKM_ECDSA_SHA384, + {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY | CKF_EC_F_P | + CKF_EC_NAMEDCURVE | CKF_EC_UNCOMPRESS}}, + {CKM_ECDSA_SHA512, + {512, 4096, CKF_HW | CKF_SIGN | CKF_VERIFY | CKF_EC_F_P | CKF_EC_NAMEDCURVE | CKF_EC_UNCOMPRESS}}, {CKM_ECDSA, {160, 521, CKF_HW | CKF_SIGN | CKF_VERIFY | CKF_EC_F_P | @@ -104,11 +118,15 @@ {CKM_EC_KEY_PAIR_GEN, {160, 521, CKF_HW | CKF_GENERATE_KEY_PAIR | CKF_EC_F_P | CKF_EC_NAMEDCURVE | CKF_EC_UNCOMPRESS}}, + {CKM_ECDH1_DERIVE, + {160, 521, CKF_HW | CKF_DERIVE | CKF_EC_NAMEDCURVE | + CKF_EC_F_P | CKF_EC_UNCOMPRESS}}, {CKM_SSL3_PRE_MASTER_KEY_GEN, {48, 48, CKF_HW | CKF_GENERATE}}, {CKM_SSL3_MD5_MAC, {384, 384, CKF_SIGN | CKF_VERIFY}}, {CKM_SSL3_SHA1_MAC, {384, 384, CKF_SIGN | CKF_VERIFY}}, {CKM_SSL3_MASTER_KEY_DERIVE, {48, 48, CKF_DERIVE}}, {CKM_SSL3_KEY_AND_MAC_DERIVE, {48, 48, CKF_DERIVE}}, + {CKM_TLS_PRE_MASTER_KEY_GEN, {48, 48, CKF_HW | CKF_GENERATE}}, {CKM_TLS_KEY_AND_MAC_DERIVE, {48, 48, CKF_DERIVE}}, {CKM_GENERIC_SECRET_KEY_GEN, {80, 2048, CKF_HW | CKF_GENERATE}}, }; @@ -183,6 +201,7 @@ rc = icsf_get_attribute(d->ld, &reason, d->icsf_object, a, 1); if (rc != CKR_OK) { TRACE_DEVEL("icsf_get_attribute failed\n"); + free(a); return icsf_to_ock_err(rc, reason); } *attr = a; @@ -447,7 +466,7 @@ if (str != NULL) { for (k = 0; k < refs_len; k++) { if (!strcasecmp(refs[k].key, c->key)) { - strncpy(refs[k].addr, str, refs[i].len); + strncpy(refs[k].addr, str, refs[k].len); refs[k].addr[refs[k].len - 1] = '\0'; goto found; } @@ -784,21 +803,22 @@ rc = XProcLock(tokdata); if (rc != CKR_OK) { TRACE_ERROR("Failed to get process lock.\n"); - goto done; + return rc; } /* Check slot data */ if (slot_data[slot_id] == NULL || !slot_data[slot_id]->initialized) { TRACE_ERROR("ICSF slot data not initialized.\n"); rc = CKR_FUNCTION_FAILED; - goto done; + XProcUnLock(tokdata); + return rc; } memcpy(&data, slot_data[slot_id], sizeof(data)); rc = XProcUnLock(tokdata); if (rc != CKR_OK) { TRACE_ERROR("Failed to release process lock.\n"); - goto done; + return rc; } if (data.mech == ICSF_CFG_MECH_SIMPLE) { @@ -1003,6 +1023,8 @@ /* Check pin */ rc = compute_sha1(tokdata, pin, pin_len, hash_sha); + if (rc != CKR_OK) + goto done; if (memcmp(tokdata->nv_token_data->so_pin_sha, hash_sha, SHA1_HASH_SIZE) != 0) { TRACE_ERROR("%s\n", ock_err(ERR_PIN_INCORRECT)); @@ -1220,7 +1242,7 @@ SHA1_HASH_SIZE); tokdata->nv_token_data->token_info.flags &= ~(CKF_SO_PIN_TO_BE_CHANGED); - XProcUnLock(tokdata); + rc = XProcUnLock(tokdata); if (rc != CKR_OK) { TRACE_ERROR("Process Lock Failed.\n"); return rc; @@ -1265,7 +1287,7 @@ /* ok got the passwd, perform simple ldap bind call */ rc = icsf_login(&new_ld, slot_data[slot_id]->uri, slot_data[slot_id]->dn, (char *)racfpwd); - if (rc != CKR_OK) { + if (rc != 0) { TRACE_DEVEL("Failed to bind to ldap server.\n"); return NULL; } @@ -1275,7 +1297,7 @@ slot_data[slot_id]->cert_file, slot_data[slot_id]->key_file, slot_data[slot_id]->ca_file, ca_dir); - if (rc != CKR_OK) { + if (rc != 0) { TRACE_DEVEL("Failed to bind to ldap server.\n"); return NULL; } @@ -1558,13 +1580,15 @@ if (slot_data[slot_id]->mech == ICSF_CFG_MECH_SIMPLE) { if (get_pk_dir(tokdata, fname, PATH_MAX) == NULL) { TRACE_ERROR("pk_dir buffer overflow\n"); - return CKR_FUNCTION_FAILED; + rc = CKR_FUNCTION_FAILED; + goto done; } if (PATH_MAX - strlen(fname) > strlen("/MK_USER")) { strcat(fname, "/MK_USER"); } else { TRACE_ERROR("MK_USER buffer overflow\n"); - return CKR_FUNCTION_FAILED; + rc = CKR_FUNCTION_FAILED; + goto done; } rc = get_masterkey(tokdata, pPin, ulPinLen, fname, tokdata->master_key, &mklen); @@ -1588,13 +1612,15 @@ /* now load the master key */ if (get_pk_dir(tokdata, fname, PATH_MAX) == NULL) { TRACE_ERROR("pk_dir buffer overflow\n"); - return CKR_FUNCTION_FAILED; + rc = CKR_FUNCTION_FAILED; + goto done; } if (PATH_MAX - strlen(fname) > strlen("/MK_SO")) { strcat(fname, "/MK_SO"); } else { TRACE_ERROR("MK_SO buffer overflow\n"); - return CKR_FUNCTION_FAILED; + rc = CKR_FUNCTION_FAILED; + goto done; } rc = get_masterkey(tokdata, pPin, ulPinLen, fname, tokdata->master_key, &mklen); @@ -1974,6 +2000,7 @@ case CKM_DES3_KEY_GEN: return CKK_DES3; case CKM_SSL3_PRE_MASTER_KEY_GEN: + case CKM_TLS_PRE_MASTER_KEY_GEN: return CKK_GENERIC_SECRET; /* Asymmetric keys */ case CKM_RSA_PKCS_KEY_PAIR_GEN: @@ -2252,7 +2279,8 @@ *handle = node_number; done: - if (rc == CKR_OK && tokdata->statistics->increment_func != NULL) + if (rc == CKR_OK && tokdata->statistics->increment_func != NULL && + mapping != NULL) tokdata->statistics->increment_func(tokdata->statistics, session->session_info.slotID, mech, mapping->strength.strength); @@ -2683,8 +2711,9 @@ goto done; } memcpy(buffer, multi_part_ctx->data, multi_part_ctx->used_data_len); - memcpy(buffer + multi_part_ctx->used_data_len, input_part, - input_part_len - remaining); + if (input_part_len - remaining > 0) + memcpy(buffer + multi_part_ctx->used_data_len, input_part, + input_part_len - remaining); /* Encrypt data using remote token. */ rc = icsf_secret_key_encrypt(session_state->ld, &reason, @@ -2741,8 +2770,10 @@ if (!is_length_only) { /* Copy remaining part of input_part into context */ if (total < multi_part_ctx->data_len) { - memcpy(multi_part_ctx->data + - multi_part_ctx->used_data_len, input_part, input_part_len); + if (input_part_len > 0) + memcpy(multi_part_ctx->data + + multi_part_ctx->used_data_len, input_part, + input_part_len); } else { memcpy(multi_part_ctx->data, input_part + input_part_len - remaining, remaining); @@ -3217,8 +3248,9 @@ goto done; } memcpy(buffer, multi_part_ctx->data, multi_part_ctx->used_data_len); - memcpy(buffer + multi_part_ctx->used_data_len, input_part, - input_part_len - remaining); + if (input_part_len - remaining > 0) + memcpy(buffer + multi_part_ctx->used_data_len, input_part, + input_part_len - remaining); /* Decrypt data using remote token. */ rc = icsf_secret_key_decrypt(session_state->ld, &reason, @@ -3274,8 +3306,10 @@ /* Copy remaining part of input_part into context */ if (total < multi_part_ctx->data_len || (padding && total == multi_part_ctx->data_len)) { - memcpy(multi_part_ctx->data + - multi_part_ctx->used_data_len, input_part, input_part_len); + if (input_part_len > 0) + memcpy(multi_part_ctx->data + + multi_part_ctx->used_data_len, input_part, + input_part_len); } else { memcpy(multi_part_ctx->data, input_part + input_part_len - remaining, remaining); @@ -3866,6 +3900,8 @@ case CKM_SHA_1_HMAC: case CKM_SSL3_SHA1_MAC: return SHA1_HASH_SIZE; + case CKM_SHA224_HMAC: + return SHA224_HASH_SIZE; case CKM_SHA256_HMAC: return SHA256_HASH_SIZE; case CKM_SHA384_HMAC: @@ -3929,6 +3965,7 @@ break; case CKM_MD5_HMAC: case CKM_SHA_1_HMAC: + case CKM_SHA224_HMAC: case CKM_SHA256_HMAC: case CKM_SHA384_HMAC: case CKM_SHA512_HMAC: @@ -3962,11 +3999,16 @@ break; case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: /* these can do mulitpart and require data caching * and do not require a mechanism parameter. */ @@ -4101,6 +4143,7 @@ switch (ctx->mech.mechanism) { case CKM_MD5_HMAC: case CKM_SHA_1_HMAC: + case CKM_SHA224_HMAC: case CKM_SHA256_HMAC: case CKM_SHA384_HMAC: case CKM_SHA512_HMAC: @@ -4146,11 +4189,16 @@ break; case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: rc = icsf_hash_signverify(session_state->ld, &reason, &mapping->icsf_object, &ctx->mech, "ONLY", (char *)in_data, in_data_len, @@ -4239,6 +4287,7 @@ switch (ctx->mech.mechanism) { case CKM_MD5_HMAC: case CKM_SHA_1_HMAC: + case CKM_SHA224_HMAC: case CKM_SHA256_HMAC: case CKM_SHA384_HMAC: case CKM_SHA512_HMAC: @@ -4260,11 +4309,16 @@ break; case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: /* caching data since ICSF wants in multiple of blocksize */ if (multi_part_ctx && multi_part_ctx->data) { @@ -4273,8 +4327,9 @@ /* if not enough to meet blocksize, cache and exit. */ if (total < multi_part_ctx->data_len) { - memcpy(multi_part_ctx->data + multi_part_ctx->used_data_len, - (char *)in_data, in_data_len); + if (in_data_len > 0) + memcpy(multi_part_ctx->data + multi_part_ctx->used_data_len, + (char *)in_data, in_data_len); multi_part_ctx->used_data_len += in_data_len; rc = CKR_OK; @@ -4292,9 +4347,10 @@ } memcpy(buffer, multi_part_ctx->data, multi_part_ctx->used_data_len); - memcpy(buffer + multi_part_ctx->used_data_len, - (char *)in_data, - out_len - multi_part_ctx->used_data_len); + if (out_len - multi_part_ctx->used_data_len > 0) + memcpy(buffer + multi_part_ctx->used_data_len, + (char *)in_data, + out_len - multi_part_ctx->used_data_len); /* copy remainder of data to ctx * for next time. caching. @@ -4392,6 +4448,7 @@ switch (ctx->mech.mechanism) { case CKM_MD5_HMAC: case CKM_SHA_1_HMAC: + case CKM_SHA224_HMAC: case CKM_SHA256_HMAC: case CKM_SHA384_HMAC: case CKM_SHA512_HMAC: @@ -4418,11 +4475,16 @@ break; case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: /* see if any data left in the cache */ if (multi_part_ctx && multi_part_ctx->used_data_len) { if (!(buffer = malloc(multi_part_ctx->used_data_len))) { @@ -4522,6 +4584,7 @@ break; case CKM_MD5_HMAC: case CKM_SHA_1_HMAC: + case CKM_SHA224_HMAC: case CKM_SHA256_HMAC: case CKM_SHA384_HMAC: case CKM_SHA512_HMAC: @@ -4557,11 +4620,16 @@ break; case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: /* these can do mulitpart and require data caching * but do not require a mechanism parameter */ @@ -4698,6 +4766,7 @@ switch (ctx->mech.mechanism) { case CKM_MD5_HMAC: case CKM_SHA_1_HMAC: + case CKM_SHA224_HMAC: case CKM_SHA256_HMAC: case CKM_SHA384_HMAC: case CKM_SHA512_HMAC: @@ -4725,11 +4794,16 @@ break; case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: rc = icsf_hash_signverify(session_state->ld, &reason, &mapping->icsf_object, &ctx->mech, "ONLY", (char *)in_data, in_data_len, @@ -4809,6 +4883,7 @@ switch (ctx->mech.mechanism) { case CKM_MD5_HMAC: case CKM_SHA_1_HMAC: + case CKM_SHA224_HMAC: case CKM_SHA256_HMAC: case CKM_SHA384_HMAC: case CKM_SHA512_HMAC: @@ -4830,11 +4905,16 @@ break; case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: /* caching data since ICSF wants in multiple of blocksize */ if (multi_part_ctx && multi_part_ctx->data) { @@ -4843,8 +4923,9 @@ /* if not enough to meet blocksize, cache and exit. */ if (total < multi_part_ctx->data_len) { - memcpy(multi_part_ctx->data + multi_part_ctx->used_data_len, - (char *)in_data, in_data_len); + if (in_data_len > 0) + memcpy(multi_part_ctx->data + multi_part_ctx->used_data_len, + (char *)in_data, in_data_len); multi_part_ctx->used_data_len += in_data_len; rc = CKR_OK; @@ -4862,9 +4943,10 @@ } memcpy(buffer, multi_part_ctx->data, multi_part_ctx->used_data_len); - memcpy(buffer + multi_part_ctx->used_data_len, - (char *)in_data, - out_len - multi_part_ctx->used_data_len); + if (out_len - multi_part_ctx->used_data_len > 0) + memcpy(buffer + multi_part_ctx->used_data_len, + (char *)in_data, + out_len - multi_part_ctx->used_data_len); /* copy remainder of data to ctx * for next time. caching. @@ -4968,6 +5050,7 @@ switch (ctx->mech.mechanism) { case CKM_MD5_HMAC: case CKM_SHA_1_HMAC: + case CKM_SHA224_HMAC: case CKM_SHA256_HMAC: case CKM_SHA384_HMAC: case CKM_SHA512_HMAC: @@ -4985,11 +5068,16 @@ break; case CKM_MD5_RSA_PKCS: case CKM_SHA1_RSA_PKCS: + case CKM_SHA224_RSA_PKCS: case CKM_SHA256_RSA_PKCS: case CKM_SHA384_RSA_PKCS: case CKM_SHA512_RSA_PKCS: case CKM_DSA_SHA1: case CKM_ECDSA_SHA1: + case CKM_ECDSA_SHA224: + case CKM_ECDSA_SHA256: + case CKM_ECDSA_SHA384: + case CKM_ECDSA_SHA512: /* see if any data left in the cache */ if (multi_part_ctx && multi_part_ctx->used_data_len) { if (!(buffer = malloc(multi_part_ctx->used_data_len))) { diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/icsf_stdll.mk opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/icsf_stdll.mk --- opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/icsf_stdll.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/icsf_stdll.mk 2023-02-13 09:22:42.000000000 +0100 @@ -7,7 +7,7 @@ usr/lib/icsf_stdll/tok_struct.h opencryptoki_stdll_libpkcs11_icsf_la_CFLAGS = \ - -DNOCDMF -DNODSA -DNODH -DMMAP -I${srcdir}/usr/lib/icsf_stdll \ + -DNODSA -DNODH -DMMAP -I${srcdir}/usr/lib/icsf_stdll \ -I${srcdir}/usr/lib/common -I${srcdir}/usr/include \ -DSTDLL_NAME=\"icsftok\" \ -DTOK_NEW_DATA_STORE=0xffffffff \ @@ -43,8 +43,9 @@ usr/lib/icsf_stdll/icsf_specific.c \ usr/lib/icsf_stdll/icsf.c usr/lib/common/utility_common.c \ usr/lib/common/ec_supported.c usr/lib/api/policyhelper.c \ - usr/lib/config/configuration.c \ - usr/lib/config/cfgparse.y usr/lib/config/cfglex.l + usr/lib/config/configuration.c usr/lib/common/pqc_supported.c \ + usr/lib/config/cfgparse.y usr/lib/config/cfglex.l \ + usr/lib/common/mech_openssl.c if ENABLE_LOCKS opencryptoki_stdll_libpkcs11_icsf_la_SOURCES += \ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/new_host.c opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/new_host.c --- opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/new_host.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/new_host.c 2023-02-13 09:22:42.000000000 +0100 @@ -702,7 +702,7 @@ //set the handle into the session. sess->handle = sSession->sessionh; - rc = session_mgr_get_op_state(sess, length_only, pOperationState, + rc = session_mgr_get_op_state(tokdata, sess, length_only, pOperationState, pulOperationStateLen); if (rc != CKR_OK) TRACE_DEVEL("session_mgr_get_op_state() failed.\n"); @@ -766,6 +766,35 @@ return rc; } +CK_RV SC_SessionCancel(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, + CK_FLAGS flags) +{ + SESSION *sess = NULL; + CK_RV rc = CKR_OK; + + if (tokdata->initialized == FALSE) { + TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); + rc = CKR_CRYPTOKI_NOT_INITIALIZED; + goto done; + } + + sess = session_mgr_find(tokdata, sSession->sessionh); + if (!sess) { + TRACE_ERROR("%s\n", ock_err(ERR_SESSION_HANDLE_INVALID)); + rc = CKR_SESSION_HANDLE_INVALID; + goto done; + } + + rc = session_mgr_cancel(tokdata, sess, flags); + +done: + TRACE_INFO("SC_SessionCancel: sess = %lu\n", sSession->sessionh); + + if (sess != NULL) + session_mgr_put(tokdata, sess); + + return rc; +} CK_RV SC_Login(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, CK_USER_TYPE userType, CK_CHAR_PTR pPin, CK_ULONG ulPinLen) @@ -1179,7 +1208,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); if (rc == CKR_OK && attr->ulValueLen != CK_UNAVAILABLE_INFORMATION) { @@ -1238,7 +1267,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -1305,7 +1334,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -2655,20 +2684,17 @@ CK_ULONG ulPartLen, CK_BYTE_PTR pEncryptedPart, CK_ULONG_PTR pulEncryptedPartLen) { - UNUSED(sSession); - UNUSED(pPart); - UNUSED(ulPartLen); - UNUSED(pEncryptedPart); - UNUSED(pulEncryptedPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_EncryptUpdate(tokdata, sSession, pPart, ulPartLen, + pEncryptedPart, pulEncryptedPartLen); + if (rc != CKR_OK || pEncryptedPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_DigestUpdate(tokdata, sSession, pPart, ulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -2678,20 +2704,17 @@ CK_ULONG ulEncryptedPartLen, CK_BYTE_PTR pPart, CK_ULONG_PTR pulPartLen) { - UNUSED(sSession); - UNUSED(pEncryptedPart); - UNUSED(ulEncryptedPartLen); - UNUSED(pPart); - UNUSED(pulPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_DecryptUpdate(tokdata, sSession, pEncryptedPart, + ulEncryptedPartLen, pPart, pulPartLen); + if (rc != CKR_OK || pPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_DigestUpdate(tokdata, sSession, pPart, *pulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -2700,43 +2723,36 @@ CK_ULONG ulPartLen, CK_BYTE_PTR pEncryptedPart, CK_ULONG_PTR pulEncryptedPartLen) { - UNUSED(sSession); - UNUSED(pPart); - UNUSED(ulPartLen); - UNUSED(pEncryptedPart); - UNUSED(pulEncryptedPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_EncryptUpdate(tokdata, sSession, pPart, ulPartLen, + pEncryptedPart, pulEncryptedPartLen); + if (rc != CKR_OK || pEncryptedPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_SignUpdate(tokdata, sSession, pPart, ulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } - CK_RV SC_DecryptVerifyUpdate(STDLL_TokData_t *tokdata, ST_SESSION_HANDLE *sSession, CK_BYTE_PTR pEncryptedPart, CK_ULONG ulEncryptedPartLen, CK_BYTE_PTR pPart, CK_ULONG_PTR pulPartLen) { - UNUSED(sSession); - UNUSED(pEncryptedPart); - UNUSED(ulEncryptedPartLen); - UNUSED(pPart); - UNUSED(pulPartLen); + CK_RV rc; - if (tokdata->initialized == FALSE) { - TRACE_ERROR("%s\n", ock_err(ERR_CRYPTOKI_NOT_INITIALIZED)); - return CKR_CRYPTOKI_NOT_INITIALIZED; - } + rc = SC_DecryptUpdate(tokdata, sSession, pEncryptedPart, + ulEncryptedPartLen, pPart, pulPartLen); + if (rc != CKR_OK || pPart == NULL) + goto out; - TRACE_ERROR("%s\n", ock_err(ERR_FUNCTION_NOT_SUPPORTED)); + rc = SC_VerifyUpdate(tokdata, sSession, pPart, *pulPartLen); - return CKR_FUNCTION_NOT_SUPPORTED; +out: + return rc; } @@ -2804,7 +2820,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -2902,13 +2918,13 @@ TRACE_DEBUG("Public Template:\n"); attr = pPublicKeyTemplate; - for (i = 0; i < ulPublicKeyAttributeCount; i++, attr++) { + for (i = 0; i < ulPublicKeyAttributeCount && attr != NULL; i++, attr++) { TRACE_DEBUG_DUMPATTR(attr); } TRACE_DEBUG("Private Template:\n"); attr = pPrivateKeyTemplate; - for (i = 0; i < ulPrivateKeyAttributeCount; i++, attr++) { + for (i = 0; i < ulPrivateKeyAttributeCount && attr != NULL; i++, attr++) { TRACE_DEBUG_DUMPATTR(attr); } #endif @@ -3037,7 +3053,7 @@ CK_ULONG i; attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -3074,7 +3090,9 @@ rc = CKR_ARGUMENTS_BAD; goto done; } - if (pMechanism->mechanism != CKM_SSL3_KEY_AND_MAC_DERIVE && !phKey) { + if (pMechanism->mechanism != CKM_SSL3_KEY_AND_MAC_DERIVE && + pMechanism->mechanism != CKM_TLS_KEY_AND_MAC_DERIVE && + !phKey) { TRACE_ERROR("%s\n", ock_err(ERR_ARGUMENTS_BAD)); rc = CKR_ARGUMENTS_BAD; goto done; @@ -3121,6 +3139,7 @@ if (rc == CKR_OK) { switch (pMechanism->mechanism) { case CKM_SSL3_KEY_AND_MAC_DERIVE: + case CKM_TLS_KEY_AND_MAC_DERIVE: { CK_SSL3_KEY_MAT_PARAMS *pReq; CK_SSL3_KEY_MAT_OUT *pPtr; @@ -3143,7 +3162,7 @@ } attr = pTemplate; - for (i = 0; i < ulCount; i++, attr++) { + for (i = 0; i < ulCount && attr != NULL; i++, attr++) { TRACE_DEBUG("%lu: Attribute type: 0x%08lx, Value Length: %lu\n", i, attr->type, attr->ulValueLen); @@ -3205,6 +3224,9 @@ //set the handle into the session. sess->handle = sSession->sessionh; + if (ulRandomLen == 0) + goto done; + rc = rng_generate(tokdata, pRandomData, ulRandomLen); if (rc != CKR_OK) TRACE_DEVEL("rng_generate() failed.\n"); @@ -3391,10 +3413,10 @@ function_list.ST_VerifyFinal = SC_VerifyFinal; function_list.ST_VerifyRecoverInit = SC_VerifyRecoverInit; function_list.ST_VerifyRecover = SC_VerifyRecover; - function_list.ST_DigestEncryptUpdate = NULL; // SC_DigestEncryptUpdate; - function_list.ST_DecryptDigestUpdate = NULL; // SC_DecryptDigestUpdate; - function_list.ST_SignEncryptUpdate = NULL; //SC_SignEncryptUpdate; - function_list.ST_DecryptVerifyUpdate = NULL; // SC_DecryptVerifyUpdate; + function_list.ST_DigestEncryptUpdate = SC_DigestEncryptUpdate; + function_list.ST_DecryptDigestUpdate = SC_DecryptDigestUpdate; + function_list.ST_SignEncryptUpdate = SC_SignEncryptUpdate; + function_list.ST_DecryptVerifyUpdate = SC_DecryptVerifyUpdate; function_list.ST_GenerateKey = SC_GenerateKey; function_list.ST_GenerateKeyPair = SC_GenerateKeyPair; function_list.ST_WrapKey = SC_WrapKey; @@ -3404,6 +3426,7 @@ function_list.ST_GenerateRandom = SC_GenerateRandom; function_list.ST_GetFunctionStatus = NULL; // SC_GetFunctionStatus; function_list.ST_CancelFunction = NULL; // SC_CancelFunction; + function_list.ST_SessionCancel = SC_SessionCancel; function_list.ST_IBM_ReencryptSingle = SC_IBM_ReencryptSingle; diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/tok_struct.h opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/tok_struct.h --- opencryptoki-3.18.0+dfsg/usr/lib/icsf_stdll/tok_struct.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/icsf_stdll/tok_struct.h 2023-02-13 09:22:42.000000000 +0100 @@ -106,6 +106,7 @@ NULL, // generic_secret_key_gen // AES NULL, // aes_key_gen + NULL, // aes_xts_key_gen NULL, // aes_ecb NULL, // aes_cbc NULL, // aes_ctr @@ -117,6 +118,7 @@ NULL, // aes_cfb NULL, // aes_mac NULL, // aes_cmac + NULL, // aes_xts // DSA NULL, // dsa_generate_keypair NULL, // dsa_sign diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/soft_stdll/soft_specific.c opencryptoki-3.20.0+dfsg/usr/lib/soft_stdll/soft_specific.c --- opencryptoki-3.18.0+dfsg/usr/lib/soft_stdll/soft_specific.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/soft_stdll/soft_specific.c 2023-02-13 09:22:42.000000000 +0100 @@ -65,9 +65,6 @@ #endif {CKM_DES_KEY_GEN, {8, 8, CKF_GENERATE}}, {CKM_DES3_KEY_GEN, {24, 24, CKF_GENERATE}}, -#if !(NOCDMF) - {CKM_CDMF_KEY_GEN, {0, 0, CKF_GENERATE}}, -#endif {CKM_RSA_PKCS, {512, 4096, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP | CKF_SIGN | CKF_VERIFY | CKF_SIGN_RECOVER | CKF_VERIFY_RECOVER}}, @@ -100,18 +97,14 @@ #endif /* Begin code contributed by Corrent corp. */ #if !(NODH) - {CKM_DH_PKCS_DERIVE, {512, 2048, CKF_DERIVE}}, - {CKM_DH_PKCS_KEY_PAIR_GEN, {512, 2048, CKF_GENERATE_KEY_PAIR}}, + {CKM_DH_PKCS_DERIVE, {512, 8192, CKF_DERIVE}}, + {CKM_DH_PKCS_KEY_PAIR_GEN, {512, 8192, CKF_GENERATE_KEY_PAIR}}, #endif /* End code contributed by Corrent corp. */ {CKM_DES_ECB, {8, 8, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, {CKM_DES_CBC, {8, 8, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, {CKM_DES_CBC_PAD, {8, 8, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, -#if !(NOCDMF) - {CKM_CDMF_ECB, {0, 0, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, - {CKM_CDMF_CBC, {0, 0, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, -#endif {CKM_DES3_ECB, {24, 24, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, {CKM_DES3_CBC, {24, 24, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, {CKM_DES3_CBC_PAD, @@ -181,8 +174,8 @@ {CKM_SSL3_KEY_AND_MAC_DERIVE, {48, 48, CKF_DERIVE}}, {CKM_SSL3_MD5_MAC, {384, 384, CKF_SIGN | CKF_VERIFY}}, {CKM_SSL3_SHA1_MAC, {384, 384, CKF_SIGN | CKF_VERIFY}}, -#if !(NOAES) {CKM_AES_KEY_GEN, {16, 32, CKF_GENERATE}}, + {CKM_AES_XTS_KEY_GEN, {32, 64, CKF_GENERATE}}, {CKM_AES_ECB, {16, 32, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, {CKM_AES_CBC, {16, 32, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, {CKM_AES_CBC_PAD, @@ -203,7 +196,7 @@ {CKM_AES_MAC_GENERAL, {16, 32, CKF_HW | CKF_SIGN | CKF_VERIFY}}, {CKM_AES_CMAC, {16, 32, CKF_SIGN | CKF_VERIFY}}, {CKM_AES_CMAC_GENERAL, {16, 32, CKF_SIGN | CKF_VERIFY}}, -#endif + {CKM_AES_XTS, {32, 64, CKF_ENCRYPT | CKF_DECRYPT | CKF_WRAP | CKF_UNWRAP}}, {CKM_GENERIC_SECRET_KEY_GEN, {80, 2048, CKF_GENERATE}}, #if !(NO_EC) {CKM_EC_KEY_PAIR_GEN, {160, 521, CKF_GENERATE_KEY_PAIR | @@ -526,8 +519,6 @@ openssl_specific_rsa_decrypt); } -#ifndef NOAES - CK_RV token_specific_aes_key_gen(STDLL_TokData_t *tokdata, CK_BYTE **key, CK_ULONG *len, CK_ULONG keysize, CK_BBOOL *is_opaque) @@ -541,6 +532,19 @@ return rng_generate(tokdata, *key, keysize); } +CK_RV token_specific_aes_xts_key_gen(STDLL_TokData_t *tokdata, CK_BYTE **key, + CK_ULONG *len, CK_ULONG keysize, + CK_BBOOL *is_opaque) +{ + *key = malloc(keysize); + if (*key == NULL) + return CKR_HOST_MEMORY; + *len = keysize; + *is_opaque = FALSE; + + return rng_generate(tokdata, *key, keysize); +} + CK_RV token_specific_aes_ecb(STDLL_TokData_t *tokdata, CK_BYTE *in_data, CK_ULONG in_data_len, @@ -652,7 +656,17 @@ first, last, ctx); } -#endif +CK_RV token_specific_aes_xts(STDLL_TokData_t *tokdata, + CK_BYTE *in_data, CK_ULONG in_data_len, + CK_BYTE *out_data, CK_ULONG *out_data_len, + OBJECT *key_obj, CK_BYTE *tweak, + CK_BOOL encrypt, CK_BBOOL initial, CK_BBOOL final, + CK_BYTE* iv) +{ + return openssl_specific_aes_xts(tokdata, in_data, in_data_len, + out_data, out_data_len, key_obj, + tweak, encrypt, initial, final, iv); +} /* Begin code contributed by Corrent corp. */ #ifndef NODH @@ -746,7 +760,7 @@ CK_ATTRIBUTE *temp_attr = NULL; CK_ATTRIBUTE *value_bits_attr = NULL; CK_BYTE *temp_byte = NULL, *temp_byte2 = NULL; - CK_ULONG temp_bn_len; + CK_ULONG temp_bn_len, value_bits; #if !OPENSSL_VERSION_PREREQ(3, 0) DH *dh = NULL; #else @@ -777,7 +791,7 @@ goto done; } - if ((prime_attr->ulValueLen > 256) || (prime_attr->ulValueLen < 64)) { + if ((prime_attr->ulValueLen > 1024) || (prime_attr->ulValueLen < 64)) { TRACE_ERROR("CKA_PRIME attribute value is invalid.\n"); rv = CKR_ATTRIBUTE_VALUE_INVALID; goto done; @@ -808,6 +822,12 @@ bn_p = NULL; bn_g = NULL; + /* CKA_VALUE_BITS is optional */ + if (template_attribute_get_ulong(priv_tmpl, CKA_VALUE_BITS, + &value_bits) == CKR_OK && + value_bits > 0) + DH_set_length(dh, value_bits); + params = EVP_PKEY_new(); if (params == NULL) { TRACE_ERROR("%s\n", ock_err(ERR_HOST_MEMORY)); @@ -823,24 +843,44 @@ dh = NULL; /* freed together with params */ #else tmpl = OSSL_PARAM_BLD_new(); - if (tmpl == NULL) + if (tmpl == NULL) { + rv = CKR_HOST_MEMORY; goto done; + } if (!OSSL_PARAM_BLD_push_BN(tmpl, OSSL_PKEY_PARAM_FFC_P, bn_p) || - !OSSL_PARAM_BLD_push_BN(tmpl, OSSL_PKEY_PARAM_FFC_G, bn_g)) + !OSSL_PARAM_BLD_push_BN(tmpl, OSSL_PKEY_PARAM_FFC_G, bn_g)) { + rv = CKR_FUNCTION_FAILED; goto done; + } + + /* CKA_VALUE_BITS is optional */ + if (template_attribute_get_ulong(priv_tmpl, CKA_VALUE_BITS, + &value_bits) == CKR_OK) { + if (!OSSL_PARAM_BLD_push_long(tmpl, OSSL_PKEY_PARAM_DH_PRIV_LEN, + value_bits)) { + rv = CKR_FUNCTION_FAILED; + goto done; + } + } osparams = OSSL_PARAM_BLD_to_param(tmpl); - if (osparams == NULL) + if (osparams == NULL) { + rv = CKR_FUNCTION_FAILED; goto done; + } pctx = EVP_PKEY_CTX_new_id(EVP_PKEY_DH, NULL); - if (pctx == NULL) + if (pctx == NULL) { + rv = CKR_FUNCTION_FAILED; goto done; + } if (!EVP_PKEY_fromdata_init(pctx) || - !EVP_PKEY_fromdata(pctx, ¶ms, EVP_PKEY_PUBLIC_KEY, osparams)) + !EVP_PKEY_fromdata(pctx, ¶ms, EVP_PKEY_PUBLIC_KEY, osparams)) { + rv = CKR_FUNCTION_FAILED; goto done; + } #endif ctx = EVP_PKEY_CTX_new(params, NULL); diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/soft_stdll/soft_stdll.mk opencryptoki-3.20.0+dfsg/usr/lib/soft_stdll/soft_stdll.mk --- opencryptoki-3.18.0+dfsg/usr/lib/soft_stdll/soft_stdll.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/soft_stdll/soft_stdll.mk 2023-02-13 09:22:42.000000000 +0100 @@ -3,7 +3,7 @@ noinst_HEADERS += usr/lib/soft_stdll/tok_struct.h opencryptoki_stdll_libpkcs11_sw_la_CFLAGS = \ - -DDEV -D_THREAD_SAFE -DSHALLOW=0 -DSWTOK=1 -DLITE=0 -DNOCDMF \ + -DDEV -D_THREAD_SAFE -DSHALLOW=0 -DSWTOK=1 -DLITE=0 \ -DNOMD2 -DNODSA -DNORIPE -fPIC -I${srcdir}/usr/lib/soft_stdll \ -DTOK_NEW_DATA_STORE=0x0003000c \ -I${srcdir}/usr/lib/common -I${srcdir}/usr/include \ @@ -12,7 +12,7 @@ opencryptoki_stdll_libpkcs11_sw_la_LDFLAGS = \ -shared -Wl,-z,defs,-Bsymbolic -lc -lpthread -lcrypto -lrt \ - -Wl,--version-script=${srcdir}/opencryptoki_tok.map + -llber -Wl,--version-script=${srcdir}/opencryptoki_tok.map opencryptoki_stdll_libpkcs11_sw_la_SOURCES = \ usr/lib/common/asn1.c usr/lib/common/cert.c \ @@ -36,7 +36,7 @@ usr/lib/soft_stdll/soft_specific.c usr/lib/common/attributes.c \ usr/lib/common/dlist.c usr/lib/common/mech_openssl.c \ usr/lib/common/utility_common.c usr/lib/common/ec_supported.c \ - usr/lib/api/policyhelper.c + usr/lib/api/policyhelper.c usr/lib/common/pqc_supported.c if ENABLE_LOCKS opencryptoki_stdll_libpkcs11_sw_la_SOURCES += \ diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/soft_stdll/tok_struct.h opencryptoki-3.20.0+dfsg/usr/lib/soft_stdll/tok_struct.h --- opencryptoki-3.18.0+dfsg/usr/lib/soft_stdll/tok_struct.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/soft_stdll/tok_struct.h 2023-02-13 09:22:42.000000000 +0100 @@ -137,8 +137,8 @@ &token_specific_hmac_verify_final, &token_specific_generic_secret_key_gen, // AES -#ifndef NOAES &token_specific_aes_key_gen, + &token_specific_aes_xts_key_gen, &token_specific_aes_ecb, &token_specific_aes_cbc, &token_specific_aes_ctr, @@ -150,20 +150,7 @@ &token_specific_aes_cfb, &token_specific_aes_mac, &token_specific_aes_cmac, -#else - NULL, // aes_key_gen - NULL, // aes_ecb - NULL, // aes_cbc - NULL, // aes_ctr - NULL, // aes_gcm_init - NULL, // aes_gcm - NULL, // aes_gcm_update - NULL, // aes_gcm_final - NULL, // aes_mac - NULL, // aes_cmac - NULL, // aes_ofb - NULL, // aes_cfb -#endif + &token_specific_aes_xts, // DSA NULL, // dsa_generate_keypair NULL, // dsa_sign diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/tpm_stdll/tok_struct.h opencryptoki-3.20.0+dfsg/usr/lib/tpm_stdll/tok_struct.h --- opencryptoki-3.18.0+dfsg/usr/lib/tpm_stdll/tok_struct.h 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/tpm_stdll/tok_struct.h 2023-02-13 09:22:42.000000000 +0100 @@ -97,6 +97,7 @@ NULL, // generic_secret_key_gen // AES &token_specific_aes_key_gen, + NULL, // aes_xts_key_gen &token_specific_aes_ecb, &token_specific_aes_cbc, NULL, // aes_ctr @@ -108,6 +109,7 @@ NULL, // aes_cfb NULL, // aes_mac NULL, // aes_cmac + NULL, // aes_xts // DSA NULL, // dsa_generate_keypair NULL, // dsa_sign diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/tpm_stdll/tpm_openssl.c opencryptoki-3.20.0+dfsg/usr/lib/tpm_stdll/tpm_openssl.c --- opencryptoki-3.18.0+dfsg/usr/lib/tpm_stdll/tpm_openssl.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/tpm_stdll/tpm_openssl.c 2023-02-13 09:22:42.000000000 +0100 @@ -44,7 +44,7 @@ #endif #ifdef DEBUG -void openssl_print_errors() +void openssl_print_errors(void) { #if !OPENSSL_VERSION_PREREQ(3, 0) ERR_load_ERR_strings(); @@ -245,37 +245,42 @@ #else BIGNUM *n_tmp, *p_tmp; #endif + int len; #if !OPENSSL_VERSION_PREREQ(3, 0) rsa = EVP_PKEY_get0_RSA(pkey); /* get the modulus from the RSA object */ RSA_get0_key(rsa, &n_tmp, NULL, NULL); - if ((*size_n = BN_bn2bin(n_tmp, n)) <= 0) { + if ((len = BN_bn2bin(n_tmp, n)) <= 0) { DEBUG_openssl_print_errors(); return -1; } + *size_n = len; /* get one of the primes from the RSA object */ RSA_get0_factors(rsa, &p_tmp, NULL); - if ((*size_p = BN_bn2bin(p_tmp, p)) <= 0) { + if ((len = BN_bn2bin(p_tmp, p)) <= 0) { DEBUG_openssl_print_errors(); return -1; } + *size_p = len; #else if (!EVP_PKEY_get_bn_param(pkey, OSSL_PKEY_PARAM_RSA_N, &n_tmp) || - (*size_n = BN_bn2bin(n_tmp, n)) <= 0) { + (len = BN_bn2bin(n_tmp, n)) <= 0) { DEBUG_openssl_print_errors(); BN_free(n_tmp); return -1; } + *size_n = len; BN_free(n_tmp); if (!EVP_PKEY_get_bn_param(pkey, OSSL_PKEY_PARAM_RSA_FACTOR1, &p_tmp) || - (*size_p = BN_bn2bin(p_tmp, p)) <= 0) { + (len = BN_bn2bin(p_tmp, p)) <= 0) { DEBUG_openssl_print_errors(); BN_free(p_tmp); return -1; } + *size_p = len; BN_free(p_tmp); #endif diff -Nru opencryptoki-3.18.0+dfsg/usr/lib/tpm_stdll/tpm_stdll.mk opencryptoki-3.20.0+dfsg/usr/lib/tpm_stdll/tpm_stdll.mk --- opencryptoki-3.18.0+dfsg/usr/lib/tpm_stdll/tpm_stdll.mk 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/lib/tpm_stdll/tpm_stdll.mk 2023-02-13 09:22:42.000000000 +0100 @@ -5,7 +5,7 @@ usr/lib/tpm_stdll/tok_struct.h opencryptoki_stdll_libpkcs11_tpm_la_CFLAGS = \ - -DLINUX -DNOCDMF -DNODSA -DNODH -DMMAP \ + -DLINUX -DNODSA -DNODH -DMMAP \ -DTOK_NEW_DATA_STORE=0xffffffff \ -I${srcdir}/usr/lib/tpm_stdll -I${srcdir}/usr/lib/common \ -I${srcdir}/usr/include -DSTDLL_NAME=\"tpmtok\" \ @@ -13,7 +13,7 @@ opencryptoki_stdll_libpkcs11_tpm_la_LDFLAGS = \ -shared -Wl,-z,defs,-Bsymbolic -lcrypto -ltspi -lpthread -lrt \ - -Wl,--version-script=${srcdir}/opencryptoki_tok.map + -llber -Wl,--version-script=${srcdir}/opencryptoki_tok.map opencryptoki_stdll_libpkcs11_tpm_la_SOURCES = \ usr/lib/common/asn1.c usr/lib/common/dig_mgr.c \ @@ -38,7 +38,7 @@ usr/lib/tpm_stdll/tpm_openssl.c usr/lib/tpm_stdll/tpm_util.c \ usr/lib/common/dlist.c usr/lib/common/mech_openssl.c \ usr/lib/common/utility_common.c usr/lib/common/ec_supported.c \ - usr/lib/api/policyhelper.c + usr/lib/api/policyhelper.c usr/lib/common/pqc_supported.c if ENABLE_LOCKS opencryptoki_stdll_libpkcs11_tpm_la_SOURCES += \ diff -Nru opencryptoki-3.18.0+dfsg/usr/sbin/p11sak/p11sak.c opencryptoki-3.20.0+dfsg/usr/sbin/p11sak/p11sak.c --- opencryptoki-3.18.0+dfsg/usr/sbin/p11sak/p11sak.c 2022-04-25 13:04:51.000000000 +0200 +++ opencryptoki-3.20.0+dfsg/usr/sbin/p11sak/p11sak.c 2023-02-13 09:22:42.000000000 +0100 @@ -25,7 +25,8 @@ #include #include -#include +#include +#include "uri.h" #include "p11util.h" #include "p11sak.h" #include "mechtable.h" @@ -77,7 +78,7 @@ static void load_pkcs11lib(void) { CK_RV rc; - CK_RV (*pfoo)(); + CK_RV (*getfunclist)(CK_FUNCTION_LIST_PTR_PTR ppFunctionList); const char *libname; /* check for environment variable PKCSLIB */ @@ -93,14 +94,14 @@ } /* get function list */ - *(void**) (&pfoo) = dlsym(pkcs11lib, "C_GetFunctionList"); - if (!pfoo) { + *(void**) (&getfunclist) = dlsym(pkcs11lib, "C_GetFunctionList"); + if (!getfunclist) { dlclose(pkcs11lib); fprintf(stderr, "Error: failed to resolve symbol '%s' from pkcs11 lib '%s'\n", "C_GetFunctionList", libname); exit(99); } - rc = pfoo(&funcs); + rc = getfunclist(&funcs); if (rc != CKR_OK) { dlclose(pkcs11lib); fprintf(stderr, "Error: C_GetFunctionList() on pkcs11 lib '%s' failed with rc = 0x%lX - %s)\n", @@ -111,51 +112,6 @@ atexit(unload_pkcs11lib); } -static CK_RV get_pin(char **pin, size_t *pinlen) -{ - struct termios old, new; - int nread; - char *user_input = NULL; - size_t buflen = 0; - CK_RV rc = 0; - - /* turn echoing off */ - if (tcgetattr(fileno(stdin), &old) != 0) - return -1; - - new = old; - new.c_lflag &= ~ECHO; - if (tcsetattr(fileno(stdin), TCSAFLUSH, &new) != 0) - return -1; - - /* read the pin - * Note: getline will allocate memory for user_input. free it when done. - */ - nread = getline(&user_input, &buflen, stdin); - if (nread == -1) { - rc = -1; - goto done; - } - - /* Restore terminal */ - (void) tcsetattr(fileno(stdin), TCSAFLUSH, &old); - - /* start a newline */ - printf("\n"); - fflush(stdout); - - /* strip the carriage return (if any) since not part of pin. */ - if (user_input[nread - 1] == '\n') - user_input[nread - 1] = '\0'; - *pinlen = strlen(user_input); - *pin = user_input; - -done: - if (rc != 0 && user_input) - free(user_input); - - return rc; -} /** * Translates the given key type to its string representation. */ @@ -168,10 +124,16 @@ return "3DES"; case kt_AES: return "AES"; + case kt_AES_XTS: + return "AES-XTS"; case kt_RSAPKCS: return "RSA_PKCS"; case kt_EC: return "EC"; + case kt_IBM_DILITHIUM: + return "IBM DILITHIUM"; + case kt_IBM_KYBER: + return "IBM KYBER"; case kt_GENERIC: return "GENERIC"; case kt_SECRET: @@ -203,11 +165,20 @@ case kt_AES: *a_key_type = CKK_AES; break; + case kt_AES_XTS: + *a_key_type = CKK_AES_XTS; + break; case kt_RSAPKCS: *a_key_type = CKK_RSA; break; case kt_EC: *a_key_type = CKK_EC; + break; + case kt_IBM_DILITHIUM: + *a_key_type = CKK_IBM_PQC_DILITHIUM; + break; + case kt_IBM_KYBER: + *a_key_type = CKK_IBM_PQC_KYBER; break; case kt_GENERIC: *a_key_type = CKK_GENERIC_SECRET; @@ -312,8 +283,14 @@ return "3DES"; case CKK_AES: return "AES"; + case CKK_AES_XTS: + return "AES-XTS"; case CKK_EC: return "EC"; + case CKK_IBM_PQC_DILITHIUM: + return "IBM DILILTHIUM"; + case CKK_IBM_PQC_KYBER: + return "IBM KYBER"; case CKK_RSA: return "RSA"; case CKK_DH: @@ -392,17 +369,22 @@ printf(" des\n"); printf(" 3des\n"); printf(" aes\n"); + printf(" aes-xts\n"); printf(" rsa\n"); printf(" ec\n"); + printf(" ibm-dilithium\n"); + printf(" ibm-kyber\n"); printf(" public\n"); printf(" private\n"); printf(" secret\n"); printf(" all\n"); printf("\n Options:\n"); printf(" -l, --long list output with long format\n"); - printf( - " --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --detailed-uri enable detailed PKCS#11 URI\n"); + printf(" --label LABEL filter keys by key label\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); printf(" --pin PIN pkcs11 user PIN\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); printf(" -h, --help Show this help\n\n"); } @@ -413,25 +395,27 @@ printf(" des\n"); printf(" 3des\n"); printf(" aes [128 | 192 | 256]\n"); + printf(" aes-xts [128 | 256]\n"); printf(" rsa [1024 | 2048 | 4096]\n"); printf(" ec [prime256v1 | prime192v1 | secp224r1 | secp384r1 | secp521r1 | secp256k1 | \n"); printf(" brainpoolP160r1 | brainpoolP160t1 | brainpoolP192r1 | brainpoolP192t1 | \n"); printf(" brainpoolP224r1 | brainpoolP224t1 | brainpoolP256r1 | brainpoolP256t1 | \n"); printf(" brainpoolP320r1 | brainpoolP320t1 | brainpoolP384r1 | brainpoolP384t1 | \n"); - printf(" brainpoolP512r1 | brainpoolP512t1]\n"); + printf(" brainpoolP512r1 | brainpoolP512t1 | curve25519 | curve448 | ed25519 | \n"); + printf(" ed448]\n"); + printf(" ibm-dilithium [r2_65 | r2_87 | r3_44 | r3_65 | r3_87]\n"); + printf(" ibm-kyber [r2_768 | r2_1024]\n"); printf("\n Options:\n"); - printf( - " --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); printf(" --pin PIN pkcs11 user PIN\n"); - printf( - " --label LABEL key label LABEL to be listed\n"); - printf( - " --exponent EXP set RSA exponent EXP\n"); - printf( - " --attr [M R L S E D G V W U A X N] set key attributes\n"); - printf( - " --attr [[pub_attrs]:[priv_attrs]] \n"); - printf( " for asymmetric keys: set individual key attributes, values see above\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL key label LABEL to be listed\n"); + printf(" --label PUB_LABEL:PRIV_LABEL\n"); + printf(" for asymmetric keys: set individual labels for public and private key\n"); + printf(" --exponent EXP set RSA exponent EXP\n"); + printf(" --attr [M R L S E D G V W U A X N] set key attributes\n"); + printf(" --attr [[pub_attrs]:[priv_attrs]] \n"); + printf(" for asymmetric keys: set individual key attributes, values see above\n"); printf(" -h, --help Show this help\n\n"); } @@ -442,29 +426,28 @@ printf(" des\n"); printf(" 3des\n"); printf(" aes\n"); + printf(" aes-xts\n"); printf(" rsa\n"); printf(" ec\n"); + printf(" ibm-dilithium\n"); + printf(" ibm-kyber\n"); printf("\n Options:\n"); - printf( - " --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); printf(" --pin PIN pkcs11 user PIN\n"); - printf( - " --label LABEL Key label LABEL to be removed\n"); - printf( - " -f, --force Force remove all keys of given cipher type\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL Key label LABEL to be removed\n"); + printf(" -f, --force Force remove all keys of given cipher type\n"); printf(" -h, --help Show this help\n\n"); } static void print_gen_des_help(void) { printf("\n Options:\n"); - printf( - " --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); printf(" --pin PIN pkcs11 user PIN\n"); - printf( - " --label LABEL key label LABEL to be listed\n"); - printf( - " --attr [M R L S E D G V W U A X N] set key attributes\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL key label LABEL to be listed\n"); + printf(" --attr [M R L S E D G V W U A X N] set key attributes\n"); printf(" -h, --help Show this help\n\n"); } @@ -476,13 +459,26 @@ printf(" 192\n"); printf(" 256\n"); printf("\n Options:\n"); - printf( - " --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --pin PIN pkcs11 user PIN\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL key label LABEL to be listed\n"); + printf(" --attr [M R L S E D G V W U A X N] set key attributes\n"); + printf(" -h, --help Show this help\n\n"); +} + +static void print_gen_aes_xts_help(void) +{ + printf("\n Usage: p11sak generate-key aes-xts [ARGS] [OPTIONS]\n"); + printf("\n Args:\n"); + printf(" 128\n"); + printf(" 256\n"); + printf("\n Options:\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); printf(" --pin PIN pkcs11 user PIN\n"); - printf( - " --label LABEL key label LABEL to be listed\n"); - printf( - " --attr [M R L S E D G V W U A X N] set key attributes\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL key label LABEL to be listed\n"); + printf(" --attr [M R L S E D G V W U A X N] set key attributes\n"); printf(" -h, --help Show this help\n\n"); } @@ -494,15 +490,16 @@ printf(" 2048\n"); printf(" 4096\n"); printf("\n Options:\n"); - printf( - " --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); printf(" --pin PIN pkcs11 user PIN\n"); - printf( - " --label LABEL key label LABEL to be listed\n"); - printf( - " --exponent EXP set RSA exponent EXP\n"); - printf( - " --attr [S D G U X] set key attributes\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL key label LABEL to be listed\n"); + printf(" --label PUB_LABEL:PRIV_LABEL\n"); + printf(" for asymmetric keys: set individual labels for public and private key\n"); + printf(" --exponent EXP set RSA exponent EXP\n"); + printf(" --attr [S D G U X] set key attributes\n"); + printf(" --attr [[pub_attrs]:[priv_attrs]] \n"); + printf(" for asymmetric keys: set individual key attributes, values see above\n"); printf(" -h, --help Show this help\n\n"); } @@ -530,16 +527,64 @@ printf(" brainpoolP384t1\n"); printf(" brainpoolP512r1\n"); printf(" brainpoolP512t1\n"); + printf(" curve25519\n"); + printf(" curve448\n"); + printf(" ed25519\n"); + printf(" ed448\n"); printf("\n Options:\n"); - printf( - " --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); printf(" --pin PIN pkcs11 user PIN\n"); - printf( - " --label LABEL key label LABEL to be listed\n"); - printf( - " --attr [S D G U X] set key attributes\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL key label LABEL to be listed\n"); + printf(" --label PUB_LABEL:PRIV_LABEL\n"); + printf(" for asymmetric keys: set individual labels for public and private key\n"); + printf(" --attr [S D G U X] set key attributes\n"); + printf(" --attr [[pub_attrs]:[priv_attrs]] \n"); + printf(" for asymmetric keys: set individual key attributes, values see above\n"); printf(" -h, --help Show this help\n\n"); } + +static void print_gen_ibm_dilithium_help(void) +{ + printf("\n Usage: p11sak generate-key ibm-dilithium [ARGS] [OPTIONS]\n"); + printf("\n Args:\n"); + printf(" r2_65\n"); + printf(" r2_87\n"); + printf(" r3_44\n"); + printf(" r3_65\n"); + printf(" r3_87\n"); + printf("\n Options:\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --pin PIN pkcs11 user PIN\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL key label LABEL to be listed\n"); + printf(" --label PUB_LABEL:PRIV_LABEL\n"); + printf(" for asymmetric keys: set individual labels for public and private key\n"); + printf(" --attr [M R L S E D G V W U A X N] set key attributes\n"); + printf(" --attr [[pub_attrs]:[priv_attrs]] \n"); + printf(" for asymmetric keys: set individual key attributes, values see above\n"); + printf(" -h, --help Show this help\n\n"); +} + +static void print_gen_ibm_kyber_help(void) +{ + printf("\n Usage: p11sak generate-key ibm-kyber [ARGS] [OPTIONS]\n"); + printf("\n Args:\n"); + printf(" r2_768\n"); + printf(" r2_1024\n"); + printf("\n Options:\n"); + printf(" --slot SLOTID openCryptoki repository token SLOTID.\n"); + printf(" --pin PIN pkcs11 user PIN\n"); + printf(" --force-pin-prompt enforce user PIN prompt\n"); + printf(" --label LABEL key label LABEL to be listed\n"); + printf(" --label PUB_LABEL:PRIV_LABEL\n"); + printf(" for asymmetric keys: set individual labels for public and private key\n"); + printf(" --attr [M R L S E D G V W U A X N] set key attributes\n"); + printf(" --attr [[pub_attrs]:[priv_attrs]] \n"); + printf(" for asymmetric keys: set individual key attributes, values see above\n"); + printf(" -h, --help Show this help\n\n"); +} + /** * Print help for generate-key command */ @@ -558,12 +603,21 @@ case kt_AES: print_gen_aes_help(); break; + case kt_AES_XTS: + print_gen_aes_xts_help(); + break; case kt_RSAPKCS: print_gen_rsa_help(); break; case kt_EC: print_gen_ec_help(); break; + case kt_IBM_DILITHIUM: + print_gen_ibm_dilithium_help(); + break; + case kt_IBM_KYBER: + print_gen_ibm_kyber_help(); + break; case no_key_type: print_gen_help(); break; @@ -597,10 +651,8 @@ printf(" 'N': CKA_NEVER_EXTRACTABLE\n"); printf("\n"); printf(" CKA_TOKEN is set by default.\n"); - printf( - " If an attribute is not set explicitly, the default values are used.\n"); - printf( - " For multiple attributes add char without white space, e. g. 'MLD')\n"); + printf(" If an attribute is not set explicitly, the default values are used.\n"); + printf(" For multiple attributes add char without white space, e. g. 'MLD')\n"); printf("\n"); printf("\n"); @@ -735,6 +787,22 @@ pubattr[*pubcount].pValue = (CK_BYTE*) brainpoolP512t1; pubattr[*pubcount].ulValueLen = sizeof(brainpoolP512t1); *keybits = 512; + } else if (strcmp(ECcurve, "curve25519") == 0) { + pubattr[*pubcount].pValue = (CK_BYTE*) curve25519; + pubattr[*pubcount].ulValueLen = sizeof(curve25519); + *keybits = 256; + } else if (strcmp(ECcurve, "curve448") == 0) { + pubattr[*pubcount].pValue = (CK_BYTE*) curve448; + pubattr[*pubcount].ulValueLen = sizeof(curve448); + *keybits = 456; + } else if (strcmp(ECcurve, "ed25519") == 0) { + pubattr[*pubcount].pValue = (CK_BYTE*) ed25519; + pubattr[*pubcount].ulValueLen = sizeof(ed25519); + *keybits = 256; + } else if (strcmp(ECcurve, "ed448") == 0) { + pubattr[*pubcount].pValue = (CK_BYTE*) ed448; + pubattr[*pubcount].ulValueLen = sizeof(ed448); + *keybits = 448; } else { fprintf(stderr, "Unexpected case while parsing EC curves.\n"); fprintf(stderr, "Note: not all tokens support all curves.\n"); @@ -745,29 +813,132 @@ return CKR_OK; } /** + * Builds the CKA_IBM_DILITHIUM_KEYFORM attribute from the given version. + */ +static CK_RV read_dilithium_args(const char *dilithium_ver, CK_ULONG *keyform, + CK_ATTRIBUTE *pubattr, CK_ULONG *pubcount) +{ + if (strcasecmp(dilithium_ver, "r2_65") == 0) { + *keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_65; + } else if (strcasecmp(dilithium_ver, "r2_87") == 0) { + *keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND2_87; + } else if (strcasecmp(dilithium_ver, "r3_44") == 0) { + *keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_44; + } else if (strcasecmp(dilithium_ver, "r3_65") == 0) { + *keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_65; + } else if (strcasecmp(dilithium_ver, "r3_87") == 0) { + *keyform = CK_IBM_DILITHIUM_KEYFORM_ROUND3_87; + } else { + fprintf(stderr, "Unexpected case while parsing dilithium version.\n"); + fprintf(stderr, "Note: not all tokens support all versions.\n"); + return CKR_ARGUMENTS_BAD; + } + + pubattr[*pubcount].type = CKA_IBM_DILITHIUM_KEYFORM; + pubattr[*pubcount].ulValueLen = sizeof(CK_ULONG); + pubattr[*pubcount].pValue = keyform; + (*pubcount)++; + + return CKR_OK; +} +/** + * Builds the CKA_IBM_KYBER_KEYFORM attribute from the given version. + */ +static CK_RV read_kyber_args(const char *kyber_ver, CK_ULONG *keyform, + CK_ATTRIBUTE *pubattr, CK_ULONG *pubcount) +{ + if (strcasecmp(kyber_ver, "r2_768") == 0) { + *keyform = CK_IBM_KYBER_KEYFORM_ROUND2_768; + } else if (strcasecmp(kyber_ver, "r2_1024") == 0) { + *keyform = CK_IBM_KYBER_KEYFORM_ROUND2_1024; + } else { + fprintf(stderr, "Unexpected case while parsing kyber version.\n"); + fprintf(stderr, "Note: not all tokens support all versions.\n"); + return CKR_ARGUMENTS_BAD; + } + + pubattr[*pubcount].type = CKA_IBM_KYBER_KEYFORM; + pubattr[*pubcount].ulValueLen = sizeof(CK_ULONG); + pubattr[*pubcount].pValue = keyform; + (*pubcount)++; + + return CKR_OK; +} +/** * Builds two CKA_LABEL attributes from given label. + * By default the specified label is extended with ":pub" and ":prv" for the + * public and private key objects. + * To set 2 different labels for public and private keys, separate them by + * colon: "pub-label:prv-label". + * To set the exact same label for public and private key, use "pub-label:=" + * To specify a colon or a equal character within a label, it must be escaped + * by a back slash: * "abc\:xyz" results in "abc:xyz". */ static CK_RV set_labelpair_attr(const char *label, CK_ATTRIBUTE *pubattr, CK_ULONG *pubcount, CK_ATTRIBUTE *prvattr, CK_ULONG *prvcount) { - char *publabel; - char *prvlabel; + char *publabel = NULL; + char *prvlabel = NULL; + unsigned int i; + + for (i = 0; i < strlen(label); i++) { + if (label[i] == '\\') { + i++; /* skip escaped character */ + continue; + } - if (!(publabel = malloc(strlen(label) + 5))) { - fprintf(stderr, "Error allocating space for publabel\n"); - return CKR_HOST_MEMORY; + if (label[i] == ':') { + if (!(publabel = strndup(label, i))) { + fprintf(stderr, "Error allocating space for publabel\n"); + return CKR_HOST_MEMORY; + } + if (!(prvlabel = strdup(&label[i + 1]))) { + fprintf(stderr, "Error allocating space for prvlabel\n"); + free(publabel); + return CKR_HOST_MEMORY; + } + break; + } } - publabel = strcpy(publabel, label); - publabel = strcat(publabel, ":pub"); - if (!(prvlabel = malloc(strlen(label) + 5))) { - fprintf(stderr, "Error allocating space for prvlabel\n"); - free(publabel); - return CKR_HOST_MEMORY; + if (publabel != NULL && prvlabel != NULL) { + if (strcmp(prvlabel, "=") == 0) { + free(prvlabel); + if (!(prvlabel = strdup(publabel))) { + fprintf(stderr, "Error allocating space for prvlabel\n"); + free(publabel); + return CKR_HOST_MEMORY; + } + } + } else { + if (!(publabel = malloc(strlen(label) + 5))) { + fprintf(stderr, "Error allocating space for publabel\n"); + return CKR_HOST_MEMORY; + } + publabel = strcpy(publabel, label); + publabel = strcat(publabel, ":pub"); + + if (!(prvlabel = malloc(strlen(label) + 5))) { + fprintf(stderr, "Error allocating space for prvlabel\n"); + free(publabel); + return CKR_HOST_MEMORY; + } + prvlabel = strcpy(prvlabel, label); + prvlabel = strcat(prvlabel, ":prv"); + } + + for (i = 0; i < strlen(publabel); i++) { + if (publabel[i] == '\\') + memmove(&publabel[i], &publabel[i + 1], + strlen(&publabel[i + 1]) + 1); + } + + for (i = 0; i < strlen(prvlabel); i++) { + if (prvlabel[i] == '\\') + memmove(&prvlabel[i], &prvlabel[i + 1], + strlen(&prvlabel[i + 1]) + 1); } - prvlabel = strcpy(prvlabel, label); - prvlabel = strcat(prvlabel, ":prv"); pubattr[*pubcount].type = CKA_LABEL; pubattr[*pubcount].pValue = publabel; @@ -798,12 +969,21 @@ case kt_AES: pmech->mechanism = CKM_AES_KEY_GEN; break; + case kt_AES_XTS: + pmech->mechanism = CKM_AES_XTS_KEY_GEN; + break; case kt_RSAPKCS: pmech->mechanism = CKM_RSA_PKCS_KEY_PAIR_GEN; break; case kt_EC: pmech->mechanism = CKM_EC_KEY_PAIR_GEN; break; + case kt_IBM_DILITHIUM: + pmech->mechanism = CKM_IBM_DILITHIUM; + break; + case kt_IBM_KYBER: + pmech->mechanism = CKM_IBM_KYBER; + break; default: return CKR_MECHANISM_INVALID; break; @@ -822,6 +1002,7 @@ case kt_DES: case kt_3DES: case kt_AES: + case kt_AES_XTS: case kt_SECRET: switch (attr_type) { case CKA_TRUSTED: @@ -929,12 +1110,10 @@ for (i = 0; i < (int) strlen(attr_string); i++) { // attr_string length is checked in parse_gen_key_args to avoid memory problems if (prv == 1 && attr_na(char2attrtype(toupper(attr_string[i])), kt_PRIVATE) == 0) { - printf("private: %d\n", attr_string[i]); set_bool_attr_from_string(&attr[*count], attr_string[i]); (*count)++; } if (prv == 0 && attr_na(char2attrtype(toupper(attr_string[i])), kt_PUBLIC) == 0) { - printf("public: %d\n", attr_string[i]); set_bool_attr_from_string(&attr[*count], attr_string[i]); (*count)++; } @@ -979,6 +1158,7 @@ case CKM_DES_KEY_GEN: case CKM_DES3_KEY_GEN: case CKM_AES_KEY_GEN: + case CKM_AES_XTS_KEY_GEN: keybits /= 8; /* mechinfo reports key size in bytes */ break; } @@ -1039,10 +1219,10 @@ rc = funcs->C_GenerateKey(session, pmech, key_attr, num_attrs, phkey); if (rc != CKR_OK) { if (is_rejected_by_policy(rc, session)) { - fprintf(stderr, "Key generation of key of length %ld bytes is rejected by policy\n", + fprintf(stderr, "Key generation of key of length %lu bytes is rejected by policy\n", a_value_len); } else { - fprintf(stderr, "Key generation of key of length %ld bytes failed\n", + fprintf(stderr, "Key generation of key of length %lu bytes failed\n", a_value_len); fprintf(stderr, "in tok_key_gen() (error code 0x%lX: %s)\n", rc, p11_get_ckr(rc)); @@ -1075,6 +1255,10 @@ if (rc != CKR_OK) { if (is_rejected_by_policy(rc, session)) fprintf(stderr, "Key pair generation rejected by policy\n"); + else if (kt == kt_IBM_DILITHIUM && rc == CKR_KEY_SIZE_RANGE) + fprintf(stderr, "IBM Dilithum version is not supported\n"); + else if (kt == kt_IBM_KYBER && rc == CKR_KEY_SIZE_RANGE) + fprintf(stderr, "IBM Kyber version is not supported\n"); else fprintf(stderr, "Key pair generation failed (error code 0x%lX: %s)\n", rc, p11_get_ckr(rc)); @@ -1092,7 +1276,7 @@ char *label) { CK_RV rc; - CK_ULONG count; + CK_ULONG count = 0; /* Boolean Attributes */ CK_BBOOL a_token; @@ -1105,9 +1289,10 @@ CK_ATTRIBUTE tmplt[3]; a_token = CK_TRUE; - tmplt[0].type = CKA_TOKEN; - tmplt[0].pValue = &a_token; - tmplt[0].ulValueLen = bs; + tmplt[count].type = CKA_TOKEN; + tmplt[count].pValue = &a_token; + tmplt[count].ulValueLen = bs; + count++; if (kt < kt_SECRET) { rc = kt2CKK(kt, &a_key_type); @@ -1116,15 +1301,7 @@ p11_get_ckr(rc)); return rc; } - } else if (kt == kt_ALL) { - rc = funcs->C_FindObjectsInit(session, NULL, 0); - if (rc != CKR_OK) { - fprintf(stderr, "C_FindObjectInit failed in tok_key_list_init() (error code 0x%lX: %s)\n", rc, - p11_get_ckr(rc)); - return rc; - } - return rc; - } else { + } else if (kt != kt_ALL) { rc = kt2CKO(kt, &a_cko); if (rc != CKR_OK) { fprintf(stderr, "Keyobject could not be set (error code 0x%lX: %s)\n", rc, @@ -1138,19 +1315,26 @@ case kt_DES: case kt_3DES: case kt_AES: + case kt_AES_XTS: case kt_GENERIC: case kt_RSAPKCS: case kt_EC: - tmplt[1].type = CKA_KEY_TYPE; - tmplt[1].pValue = &a_key_type; - tmplt[1].ulValueLen = sizeof(CK_KEY_TYPE); + case kt_IBM_DILITHIUM: + case kt_IBM_KYBER: + tmplt[count].type = CKA_KEY_TYPE; + tmplt[count].pValue = &a_key_type; + tmplt[count].ulValueLen = sizeof(CK_KEY_TYPE); + count++; break; case kt_SECRET: case kt_PUBLIC: case kt_PRIVATE: - tmplt[1].type = CKA_CLASS; - tmplt[1].pValue = &a_cko; - tmplt[1].ulValueLen = sizeof(CK_OBJECT_CLASS); + tmplt[count].type = CKA_CLASS; + tmplt[count].pValue = &a_cko; + tmplt[count].ulValueLen = sizeof(CK_OBJECT_CLASS); + count++; + break; + case kt_ALL: break; default: fprintf(stderr, "Unknown key type\n"); @@ -1158,12 +1342,11 @@ } if (label != NULL_PTR) { - tmplt[2].type = CKA_LABEL; - tmplt[2].pValue = label; - tmplt[2].ulValueLen = strlen(label); - count = 3; - } else - count = 2; + tmplt[count].type = CKA_LABEL; + tmplt[count].pValue = label; + tmplt[count].ulValueLen = strlen(label); + count++; + } rc = funcs->C_FindObjectsInit(session, tmplt, count); if (rc != CKR_OK) { @@ -1226,7 +1409,7 @@ int f; struct ConfigBaseNode *c, *name, *hex_string, *type; struct ConfigStructNode *structnode; - int def_attr; + int def_attr = 0; if (cfg != NULL) { @@ -1622,6 +1805,58 @@ return CKR_OK; } + +/** + * Alloc attribute + */ +static CK_RV tok_attribute_alloc(CK_SESSION_HANDLE session, + CK_OBJECT_HANDLE hkey, + CK_ATTRIBUTE_PTR attribute) +{ + CK_RV rv; + void *tmp; + + if (!attribute) + return CKR_ARGUMENTS_BAD; + + if (attribute->pValue) + return CKR_CANCEL; + + if (attribute->ulValueLen) + goto alloc; + + /* lookup size */ + rv = funcs->C_GetAttributeValue(session, hkey, attribute, 1); + if ((rv == CKR_ATTRIBUTE_SENSITIVE) || + (attribute->ulValueLen == 0) || + (attribute->ulValueLen == CK_UNAVAILABLE_INFORMATION)) { + /** + * REVISIT if the attribute is not available, the first + * returns with ulValueLen == 0. According to the spec a + * return value CKR_ATTRIBUTE_SENSITIVE is expected. Check + * implementation and spec for clarification. + **/ + attribute->pValue = NULL_PTR; + attribute->ulValueLen = 0; + return CKR_ATTRIBUTE_SENSITIVE; + } + if (rv != CKR_OK) { + fprintf(stderr, + "Object can not lookup attribute length " + "(error code 0x%lX: %s)\n", rv, p11_get_ckr(rv)); + return rv; + } + +alloc: + tmp = malloc((size_t) attribute->ulValueLen); + if (!tmp) + return CKR_HOST_MEMORY; + + attribute->pValue = tmp; + + return CKR_OK; +} + /** * Get label attribute of key */ @@ -1716,10 +1951,8 @@ strcpy(buffer, "private "); break; default: - // FIXIT - return code to represent object class invalid - rc = CKR_KEY_HANDLE_INVALID; - fprintf(stderr, "Object handle invalid (error code 0x%lX: %s)\n", - rc, p11_get_ckr(rc)); + /* its not a key */ + rc = CKR_KEY_TYPE_INCONSISTENT; free(buffer); return rc; } @@ -1740,6 +1973,7 @@ *klength = 0; switch (kt) { case CKK_AES: + case CKK_AES_XTS: case CKK_GENERIC_SECRET: template[0].type = CKA_VALUE_LEN; template[0].pValue = &vl; @@ -1752,6 +1986,8 @@ return rc; } *klength = vl * 8; + if (kt == CKK_AES_XTS) + *klength /= 2; break; default: // Fall through - template values set above @@ -1768,18 +2004,61 @@ * Check args for gen_key command. */ static CK_RV check_args_gen_key(p11sak_kt *kt, CK_ULONG keylength, - char *ECcurve) + char *ECcurve, char *pqc_ver) { switch (*kt) { case kt_DES: case kt_3DES: break; + case kt_IBM_DILITHIUM: + if (pqc_ver == NULL) { + fprintf(stderr, + "Cipher key type [%d] supported but Dilithium version not set in arguments. Try adding argument , , , , or \n", + *kt); + return CKR_ARGUMENTS_BAD; + } + if (strcasecmp(pqc_ver, "r2_65") == 0 || + strcasecmp(pqc_ver, "r2_87") == 0 || + strcasecmp(pqc_ver, "r3_44") == 0 || + strcasecmp(pqc_ver, "r3_65") == 0 || + strcasecmp(pqc_ver, "r3_87") == 0) { + break; + } else { + fprintf(stderr, "IBM Dilithium version [%s] not supported \n", pqc_ver); + return CKR_ARGUMENTS_BAD; + } + break; + case kt_IBM_KYBER: + if (pqc_ver == NULL) { + fprintf(stderr, + "Cipher key type [%d] supported but Kyber version not set in arguments. Try adding argument or \n", + *kt); + return CKR_ARGUMENTS_BAD; + } + if (strcasecmp(pqc_ver, "r2_768") == 0 || + strcasecmp(pqc_ver, "r2_1024") == 0) { + break; + } else { + fprintf(stderr, "IBM Kyber version [%s] not supported \n", pqc_ver); + return CKR_ARGUMENTS_BAD; + } + break; case kt_AES: if ((keylength == 128) || (keylength == 192) || (keylength == 256)) { break; } else { fprintf(stderr, - "Cipher key type [%d] and key bit length %ld is not supported. Try adding argument -bits <128|192|256>\n", + "Cipher key type [%d] and key bit length %lu is not supported. Try adding argument <128|192|256>\n", + *kt, keylength); + return CKR_ARGUMENTS_BAD; + } + break; + case kt_AES_XTS: + if ((keylength == 128) || (keylength == 256)) { + break; + } else { + fprintf(stderr, + "Cipher key type [%d] and key bit length %lu is not supported. Try adding argument <128|256>\n", *kt, keylength); return CKR_ARGUMENTS_BAD; } @@ -1789,14 +2068,14 @@ break; } else { fprintf(stderr, - "[%d] RSA modulus bit length %ld NOT supported. Try adding argument -bits <1024|2048|4096>\n", + "[%d] RSA modulus bit length %lu NOT supported. Try adding argument <1024|2048|4096>\n", *kt, keylength); } break; case kt_EC: if (ECcurve == NULL) { fprintf(stderr, - "Cipher key type [%d] supported but EC curve not set in arguments. Try argument -curve \n", + "Cipher key type [%d] supported but EC curve not set in arguments. Try argument \n", *kt); return CKR_ARGUMENTS_BAD; } @@ -1821,10 +2100,13 @@ { switch (*kt) { case kt_AES: + case kt_AES_XTS: case kt_RSAPKCS: case kt_DES: case kt_3DES: case kt_EC: + case kt_IBM_DILITHIUM: + case kt_IBM_KYBER: case kt_GENERIC: case kt_SECRET: case kt_PUBLIC: @@ -1848,8 +2130,11 @@ case kt_DES: case kt_3DES: case kt_AES: + case kt_AES_XTS: case kt_RSAPKCS: case kt_EC: + case kt_IBM_DILITHIUM: + case kt_IBM_KYBER: case kt_GENERIC: case kt_SECRET: case kt_PUBLIC: @@ -1916,7 +2201,8 @@ */ static CK_RV parse_list_key_args(char *argv[], int argc, p11sak_kt *kt, CK_ULONG *keylength, CK_SLOT_ID *slot, - char **pin, int *long_print) + const char **pin, int *long_print, char **label, + int *full_uri, int *force_pin_prompt) { CK_RV rc; CK_BBOOL slotIDset = CK_FALSE; @@ -1932,32 +2218,32 @@ for (i = 2; i < argc; i++) { /* Get arguments */ - if (strcmp(argv[i], "DES") == 0 || strcmp(argv[i], "des") == 0) { + if (strcasecmp(argv[i], "des") == 0) { *kt = kt_DES; *keylength = 64; - } else if (strcmp(argv[i], "3DES") == 0 - || strcmp(argv[i], "3des") == 0) { + } else if (strcasecmp(argv[i], "3des") == 0) { *kt = kt_3DES; - } else if (strcmp(argv[i], "AES") == 0 || strcmp(argv[i], "aes") == 0) { + } else if (strcasecmp(argv[i], "aes") == 0) { *kt = kt_AES; - } else if (strcmp(argv[i], "RSA") == 0 || strcmp(argv[i], "rsa") == 0) { + } else if (strcasecmp(argv[i], "aes-xts") == 0) { + *kt = kt_AES_XTS; + } else if (strcasecmp(argv[i], "rsa") == 0) { *kt = kt_RSAPKCS; - } else if (strcmp(argv[i], "EC") == 0 || strcmp(argv[i], "ec") == 0) { + } else if (strcasecmp(argv[i], "ec") == 0) { *kt = kt_EC; - } else if (strcmp(argv[i], "GENERIC") == 0 - || strcmp(argv[i], "generic") == 0) { + } else if (strcasecmp(argv[i], "ibm-dilithium") == 0) { + *kt = kt_IBM_DILITHIUM; + } else if (strcasecmp(argv[i], "ibm-kyber") == 0) { + *kt = kt_IBM_KYBER; + } else if (strcasecmp(argv[i], "generic") == 0) { *kt = kt_GENERIC; - } else if (strcmp(argv[i], "SECRET") == 0 - || strcmp(argv[i], "secret") == 0) { + } else if (strcasecmp(argv[i], "secret") == 0) { *kt = kt_SECRET; - } else if (strcmp(argv[i], "PUBLIC") == 0 - || strcmp(argv[i], "public") == 0) { + } else if (strcasecmp(argv[i], "public") == 0) { *kt = kt_PUBLIC; - } else if (strcmp(argv[i], "PRIVATE") == 0 - || strcmp(argv[i], "private") == 0) { + } else if (strcasecmp(argv[i], "private") == 0) { *kt = kt_PRIVATE; - } else if (strcmp(argv[i], "ALL") == 0 - || strcmp(argv[i], "all") == 0) { + } else if (strcasecmp(argv[i], "all") == 0) { *kt = kt_ALL; /* Get options */ } else if (strcmp(argv[i], "--slot") == 0) { @@ -1999,6 +2285,18 @@ } else if ((strcmp(argv[i], "-l") == 0) || (strcmp(argv[i], "--long") == 0)) { *long_print = 1; + } else if (strcmp(argv[i], "--label") == 0) { + if (i + 1 < argc) { + *label = argv[i + 1]; + } else { + fprintf(stderr, "--label