gost_ec_sign.c
)
+set (GOST_OMAC_SOURCE_FILES
+ gost_omac.c
+ )
+
set(GOST_LIB_SOURCE_FILES
${GOST_89_SOURCE_FILES}
${GOST_HASH_SOURCE_FILES}
${GOST_HASH_2012_SOURCE_FILES}
${GOST_GRASSHOPPER_SOURCE_FILES}
${GOST_EC_SOURCE_FILES}
+ ${GOST_OMAC_SOURCE_FILES}
)
set(GOST_ENGINE_SOURCE_FILES
gost_md.c
gost_md2012.c
gost_pmeth.c
+ gost_omac.c
)
add_library(gost_core STATIC ${GOST_LIB_SOURCE_FILES})
add_executable(gost12sum ${GOST_12_SUM_SOURCE_FILES})
target_link_libraries(gost12sum gost_core)
+set_source_files_properties(tags PROPERTIES GENERATED true)
+add_custom_target(tags
+ COMMAND ctags -R . ${OPENSSL_ROOT_DIR}
+ WORKING_DIRECTORY ${CMAKE_SOURCE_DIR})
+
# install
set(OPENSSL_ENGINES_INSTALL_DIR ${CMAKE_INSTALL_LIBDIR}/engines-${OPENSSL_VERSION_MAJOR}_${OPENSSL_VERSION_MINOR})
set(OPENSSL_MAN_INSTALL_DIR ${CMAKE_INSTALL_MANDIR}/man1)
To build and install OpenSSL GOST Engine, you will need
-* OpenSSL 1.1.*
+* OpenSSL 1.1.1
* an ANSI C compiler
* CMake (3.0 or newer)
-/* e_gost_err.c */
-/* ====================================================================
- * Copyright (c) 1999-2016 The OpenSSL Project. 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. All advertising materials mentioning features or use of this
- * software must display the following acknowledgment:
- * "This product includes software developed by the OpenSSL Project
- * for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
- *
- * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
- * endorse or promote products derived from this software without
- * prior written permission. For written permission, please contact
- * openssl-core@OpenSSL.org.
- *
- * 5. Products derived from this software may not be called "OpenSSL"
- * nor may "OpenSSL" appear in their names without prior written
- * permission of the OpenSSL Project.
- *
- * 6. Redistributions of any form whatsoever must retain the following
- * acknowledgment:
- * "This product includes software developed by the OpenSSL Project
- * for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
- *
- * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
- * EXPRESSED 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 OpenSSL PROJECT OR
- * ITS 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.
- * ====================================================================
- *
- * This product includes cryptographic software written by Eric Young
- * (eay@cryptsoft.com). This product includes software written by Tim
- * Hudson (tjh@cryptsoft.com).
- *
- */
-
/*
- * NOTE: this file was auto generated by the mkerr.pl script: any changes
- * made to it will be overwritten when the script next updates this file,
- * only reason strings will be preserved.
+ * Generated by util/mkerr.pl DO NOT EDIT
+ * Copyright 1995-2018 The OpenSSL Project Authors. All Rights Reserved.
+ *
+ * Licensed under the OpenSSL license (the "License"). You may not use
+ * this file except in compliance with the License. You can obtain a copy
+ * in the file LICENSE in the source distribution or at
+ * https://www.openssl.org/source/license.html
*/
-#include <stdio.h>
#include <openssl/err.h>
#include "e_gost_err.h"
-/* BEGIN ERROR CODES */
#ifndef OPENSSL_NO_ERR
-# define ERR_FUNC(func) ERR_PACK(0,func,0)
-# define ERR_REASON(reason) ERR_PACK(0,0,reason)
-
static ERR_STRING_DATA GOST_str_functs[] = {
- {ERR_FUNC(GOST_F_DECODE_GOST_ALGOR_PARAMS), "DECODE_GOST_ALGOR_PARAMS"},
- {ERR_FUNC(GOST_F_ENCODE_GOST_ALGOR_PARAMS), "ENCODE_GOST_ALGOR_PARAMS"},
- {ERR_FUNC(GOST_F_FILL_GOST_EC_PARAMS), "FILL_GOST_EC_PARAMS"},
- {ERR_FUNC(GOST_F_GET_ENCRYPTION_PARAMS), "GET_ENCRYPTION_PARAMS"},
- {ERR_FUNC(GOST_F_GOST89_GET_ASN1_PARAMETERS),
- "GOST89_GET_ASN1_PARAMETERS"},
- {ERR_FUNC(GOST_F_GOST89_SET_ASN1_PARAMETERS),
- "GOST89_SET_ASN1_PARAMETERS"},
- {ERR_FUNC(GOST_F_GOST_CIPHER_CTL), "GOST_CIPHER_CTL"},
- {ERR_FUNC(GOST_F_GOST_EC_COMPUTE_PUBLIC), "GOST_EC_COMPUTE_PUBLIC"},
- {ERR_FUNC(GOST_F_GOST_EC_KEYGEN), "GOST_EC_KEYGEN"},
- {ERR_FUNC(GOST_F_GOST_EC_SIGN), "GOST_EC_SIGN"},
- {ERR_FUNC(GOST_F_GOST_EC_VERIFY), "GOST_EC_VERIFY"},
- {ERR_FUNC(GOST_F_GOST_IMIT_CTRL), "GOST_IMIT_CTRL"},
- {ERR_FUNC(GOST_F_GOST_IMIT_FINAL), "GOST_IMIT_FINAL"},
- {ERR_FUNC(GOST_F_GOST_IMIT_UPDATE), "GOST_IMIT_UPDATE"},
- {ERR_FUNC(GOST_F_PARAM_COPY_GOST_EC), "PARAM_COPY_GOST_EC"},
- {ERR_FUNC(GOST_F_PKEY_GOST01_PARAMGEN), "PKEY_GOST01_PARAMGEN"},
- {ERR_FUNC(GOST_F_PKEY_GOST12_PARAMGEN), "PKEY_GOST12_PARAMGEN"},
- {ERR_FUNC(GOST_F_PKEY_GOST_CTRL), "PKEY_GOST_CTRL"},
- {ERR_FUNC(GOST_F_PKEY_GOST_ECCP_DECRYPT), "PKEY_GOST_ECCP_DECRYPT"},
- {ERR_FUNC(GOST_F_PKEY_GOST_ECCP_ENCRYPT), "PKEY_GOST_ECCP_ENCRYPT"},
- {ERR_FUNC(GOST_F_PKEY_GOST_EC_CTRL_STR_256), "PKEY_GOST_EC_CTRL_STR_256"},
- {ERR_FUNC(GOST_F_PKEY_GOST_EC_CTRL_STR_512), "PKEY_GOST_EC_CTRL_STR_512"},
- {ERR_FUNC(GOST_F_PKEY_GOST_EC_DERIVE), "PKEY_GOST_EC_DERIVE"},
- {ERR_FUNC(GOST_F_PKEY_GOST_MAC_CTRL), "PKEY_GOST_MAC_CTRL"},
- {ERR_FUNC(GOST_F_PKEY_GOST_MAC_CTRL_STR), "PKEY_GOST_MAC_CTRL_STR"},
- {ERR_FUNC(GOST_F_PKEY_GOST_MAC_KEYGEN), "PKEY_GOST_MAC_KEYGEN"},
- {ERR_FUNC(GOST_F_PKEY_GOST_MAC_SIGNCTX_INIT),
- "PKEY_GOST_MAC_SIGNCTX_INIT"},
- {ERR_FUNC(GOST_F_PRINT_GOST_EC_PUB), "PRINT_GOST_EC_PUB"},
- {ERR_FUNC(GOST_F_PRIV_DECODE_GOST), "PRIV_DECODE_GOST"},
- {ERR_FUNC(GOST_F_PUB_DECODE_GOST_EC), "PUB_DECODE_GOST_EC"},
- {ERR_FUNC(GOST_F_PUB_ENCODE_GOST_EC), "PUB_ENCODE_GOST_EC"},
- {ERR_FUNC(GOST_F_UNPACK_CP_SIGNATURE), "UNPACK_CP_SIGNATURE"},
- {ERR_FUNC(GOST_F_VKO_COMPUTE_KEY), "VKO_COMPUTE_KEY"},
+ {ERR_PACK(0, GOST_F_DECODE_GOST_ALGOR_PARAMS, 0),
+ "decode_gost_algor_params"},
+ {ERR_PACK(0, GOST_F_ENCODE_GOST_ALGOR_PARAMS, 0),
+ "encode_gost_algor_params"},
+ {ERR_PACK(0, GOST_F_FILL_GOST_EC_PARAMS, 0), "fill_GOST_EC_params"},
+ {ERR_PACK(0, GOST_F_GET_ENCRYPTION_PARAMS, 0), "get_encryption_params"},
+ {ERR_PACK(0, GOST_F_GOST89_GET_ASN1_PARAMETERS, 0),
+ "gost89_get_asn1_parameters"},
+ {ERR_PACK(0, GOST_F_GOST89_SET_ASN1_PARAMETERS, 0),
+ "gost89_set_asn1_parameters"},
+ {ERR_PACK(0, GOST_F_GOST_CIPHER_CTL, 0), "gost_cipher_ctl"},
+ {ERR_PACK(0, GOST_F_GOST_EC_COMPUTE_PUBLIC, 0), "gost_ec_compute_public"},
+ {ERR_PACK(0, GOST_F_GOST_EC_KEYGEN, 0), "gost_ec_keygen"},
+ {ERR_PACK(0, GOST_F_GOST_EC_SIGN, 0), "gost_ec_sign"},
+ {ERR_PACK(0, GOST_F_GOST_EC_VERIFY, 0), "gost_ec_verify"},
+ {ERR_PACK(0, GOST_F_GOST_GRASSHOPPER_CIPHER_CTL, 0),
+ "gost_grasshopper_cipher_ctl"},
+ {ERR_PACK(0, GOST_F_GOST_GRASSHOPPER_SET_ASN1_PARAMETERS, 0),
+ "gost_grasshopper_set_asn1_parameters"},
+ {ERR_PACK(0, GOST_F_GOST_IMIT_CTRL, 0), "gost_imit_ctrl"},
+ {ERR_PACK(0, GOST_F_GOST_IMIT_FINAL, 0), "gost_imit_final"},
+ {ERR_PACK(0, GOST_F_GOST_IMIT_UPDATE, 0), "gost_imit_update"},
+ {ERR_PACK(0, GOST_F_OMAC_IMIT_CTRL, 0), "omac_imit_ctrl"},
+ {ERR_PACK(0, GOST_F_OMAC_IMIT_FINAL, 0), "omac_imit_final"},
+ {ERR_PACK(0, GOST_F_OMAC_IMIT_UPDATE, 0), "omac_imit_update"},
+ {ERR_PACK(0, GOST_F_OMAC_KEY, 0), "omac_key"},
+ {ERR_PACK(0, GOST_F_PARAM_COPY_GOST_EC, 0), "param_copy_gost_ec"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST2001_PARAMGEN, 0), "pkey_gost2001_paramgen"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST2012_PARAMGEN, 0), "pkey_gost2012_paramgen"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_CTRL, 0), "pkey_gost_ctrl"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_ECCP_DECRYPT, 0), "pkey_GOST_ECcp_decrypt"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_ECCP_ENCRYPT, 0), "pkey_GOST_ECcp_encrypt"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_EC_CTRL_STR_256, 0),
+ "pkey_gost_ec_ctrl_str_256"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_EC_CTRL_STR_512, 0),
+ "pkey_gost_ec_ctrl_str_512"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_EC_DERIVE, 0), "pkey_gost_ec_derive"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_GRASSHOPPER_MAC_SIGNCTX_INIT, 0),
+ "pkey_gost_grasshopper_mac_signctx_init"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_MAC_CTRL, 0), "pkey_gost_mac_ctrl"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_MAC_CTRL_STR, 0), "pkey_gost_mac_ctrl_str"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_MAC_KEYGEN_BASE, 0),
+ "pkey_gost_mac_keygen_base"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_MAC_SIGNCTX_INIT, 0),
+ "pkey_gost_mac_signctx_init"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_MAGMA_MAC_SIGNCTX_INIT, 0),
+ "pkey_gost_magma_mac_signctx_init"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_OMAC_CTRL, 0), "pkey_gost_omac_ctrl"},
+ {ERR_PACK(0, GOST_F_PKEY_GOST_OMAC_CTRL_STR, 0), "pkey_gost_omac_ctrl_str"},
+ {ERR_PACK(0, GOST_F_PRINT_GOST_EC_PUB, 0), "print_gost_ec_pub"},
+ {ERR_PACK(0, GOST_F_PRIV_DECODE_GOST, 0), "priv_decode_gost"},
+ {ERR_PACK(0, GOST_F_PUB_DECODE_GOST_EC, 0), "pub_decode_gost_ec"},
+ {ERR_PACK(0, GOST_F_PUB_ENCODE_GOST_EC, 0), "pub_encode_gost_ec"},
+ {ERR_PACK(0, GOST_F_UNPACK_CP_SIGNATURE, 0), "unpack_cp_signature"},
+ {ERR_PACK(0, GOST_F_VKO_COMPUTE_KEY, 0), "VKO_compute_key"},
{0, NULL}
};
static ERR_STRING_DATA GOST_str_reasons[] = {
- {ERR_REASON(GOST_R_BAD_KEY_PARAMETERS_FORMAT),
- "bad key parameters format"},
- {ERR_REASON(GOST_R_BAD_PKEY_PARAMETERS_FORMAT),
- "bad pkey parameters format"},
- {ERR_REASON(GOST_R_CANNOT_PACK_EPHEMERAL_KEY),
- "cannot pack ephemeral key"},
- {ERR_REASON(GOST_R_CTRL_CALL_FAILED), "ctrl call failed"},
- {ERR_REASON(GOST_R_ERROR_COMPUTING_SHARED_KEY),
- "error computing shared key"},
- {ERR_REASON(GOST_R_ERROR_PARSING_KEY_TRANSPORT_INFO),
- "error parsing key transport info"},
- {ERR_REASON(GOST_R_ERROR_POINT_MUL), "error point mul"},
- {ERR_REASON(GOST_R_INCOMPATIBLE_ALGORITHMS), "incompatible algorithms"},
- {ERR_REASON(GOST_R_INCOMPATIBLE_PEER_KEY), "incompatible peer key"},
- {ERR_REASON(GOST_R_INVALID_CIPHER_PARAMS), "invalid cipher params"},
- {ERR_REASON(GOST_R_INVALID_CIPHER_PARAM_OID), "invalid cipher param oid"},
- {ERR_REASON(GOST_R_INVALID_DIGEST_TYPE), "invalid digest type"},
- {ERR_REASON(GOST_R_INVALID_IV_LENGTH), "invalid iv length"},
- {ERR_REASON(GOST_R_INVALID_MAC_KEY_LENGTH), "invalid mac key length"},
- {ERR_REASON(GOST_R_INVALID_MAC_KEY_SIZE), "invalid mac key size"},
- {ERR_REASON(GOST_R_INVALID_MAC_PARAMS), "invalid mac params"},
- {ERR_REASON(GOST_R_INVALID_MAC_SIZE), "invalid mac size"},
- {ERR_REASON(GOST_R_INVALID_PARAMSET), "invalid paramset"},
- {ERR_REASON(GOST_R_KEY_IS_NOT_INITIALIZED), "key is not initialized"},
- {ERR_REASON(GOST_R_KEY_PARAMETERS_MISSING), "key parameters missing"},
- {ERR_REASON(GOST_R_MAC_KEY_NOT_SET), "mac key not set"},
- {ERR_REASON(GOST_R_NO_PARAMETERS_SET), "no parameters set"},
- {ERR_REASON(GOST_R_NO_PEER_KEY), "no peer key"},
- {ERR_REASON(GOST_R_NO_PRIVATE_PART_OF_NON_EPHEMERAL_KEYPAIR),
- "no private part of non ephemeral keypair"},
- {ERR_REASON(GOST_R_PUBLIC_KEY_UNDEFINED), "public key undefined"},
- {ERR_REASON(GOST_R_RNG_ERROR), "rng error"},
- {ERR_REASON(GOST_R_SIGNATURE_MISMATCH), "signature mismatch"},
- {ERR_REASON(GOST_R_SIGNATURE_PARTS_GREATER_THAN_Q),
- "signature parts greater than q"},
- {ERR_REASON(GOST_R_UKM_NOT_SET), "ukm not set"},
- {ERR_REASON(GOST_R_UNSUPPORTED_CIPHER_CTL_COMMAND),
- "unsupported cipher ctl command"},
- {ERR_REASON(GOST_R_UNSUPPORTED_PARAMETER_SET),
- "unsupported parameter set"},
+ {ERR_PACK(0, 0, GOST_R_BAD_KEY_PARAMETERS_FORMAT),
+ "bad key parameters format"},
+ {ERR_PACK(0, 0, GOST_R_BAD_ORDER), "bad order"},
+ {ERR_PACK(0, 0, GOST_R_BAD_PKEY_PARAMETERS_FORMAT),
+ "bad pkey parameters format"},
+ {ERR_PACK(0, 0, GOST_R_CANNOT_PACK_EPHEMERAL_KEY),
+ "cannot pack ephemeral key"},
+ {ERR_PACK(0, 0, GOST_R_CIPHER_NOT_FOUND), "cipher not found"},
+ {ERR_PACK(0, 0, GOST_R_CTRL_CALL_FAILED), "ctrl call failed"},
+ {ERR_PACK(0, 0, GOST_R_ERROR_COMPUTING_SHARED_KEY),
+ "error computing shared key"},
+ {ERR_PACK(0, 0, GOST_R_ERROR_PARSING_KEY_TRANSPORT_INFO),
+ "error parsing key transport info"},
+ {ERR_PACK(0, 0, GOST_R_ERROR_POINT_MUL), "error point mul"},
+ {ERR_PACK(0, 0, GOST_R_INCOMPATIBLE_ALGORITHMS), "incompatible algorithms"},
+ {ERR_PACK(0, 0, GOST_R_INCOMPATIBLE_PEER_KEY), "incompatible peer key"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_CIPHER_PARAMS), "invalid cipher params"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_CIPHER_PARAM_OID),
+ "invalid cipher param oid"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_DIGEST_TYPE), "invalid digest type"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_IV_LENGTH), "invalid iv length"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_MAC_KEY_LENGTH), "invalid mac key length"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_MAC_KEY_SIZE), "invalid mac key size"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_MAC_PARAMS), "invalid mac params"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_MAC_SIZE), "invalid mac size"},
+ {ERR_PACK(0, 0, GOST_R_INVALID_PARAMSET), "invalid paramset"},
+ {ERR_PACK(0, 0, GOST_R_KEY_IS_NOT_INITIALIZED), "key is not initialized"},
+ {ERR_PACK(0, 0, GOST_R_KEY_PARAMETERS_MISSING), "key parameters missing"},
+ {ERR_PACK(0, 0, GOST_R_MAC_KEY_NOT_SET), "mac key not set"},
+ {ERR_PACK(0, 0, GOST_R_NO_PARAMETERS_SET), "no parameters set"},
+ {ERR_PACK(0, 0, GOST_R_NO_PEER_KEY), "no peer key"},
+ {ERR_PACK(0, 0, GOST_R_NO_PRIVATE_PART_OF_NON_EPHEMERAL_KEYPAIR),
+ "no private part of non ephemeral keypair"},
+ {ERR_PACK(0, 0, GOST_R_PUBLIC_KEY_UNDEFINED), "public key undefined"},
+ {ERR_PACK(0, 0, GOST_R_RNG_ERROR), "rng error"},
+ {ERR_PACK(0, 0, GOST_R_SIGNATURE_MISMATCH), "signature mismatch"},
+ {ERR_PACK(0, 0, GOST_R_SIGNATURE_PARTS_GREATER_THAN_Q),
+ "signature parts greater than q"},
+ {ERR_PACK(0, 0, GOST_R_UKM_NOT_SET), "ukm not set"},
+ {ERR_PACK(0, 0, GOST_R_UNSUPPORTED_CIPHER_CTL_COMMAND),
+ "unsupported cipher ctl command"},
+ {ERR_PACK(0, 0, GOST_R_UNSUPPORTED_PARAMETER_SET),
+ "unsupported parameter set"},
{0, NULL}
};
#endif
-#ifdef GOST_LIB_NAME
-static ERR_STRING_DATA GOST_lib_name[] = {
- {0, GOST_LIB_NAME},
- {0, NULL}
-};
-#endif
+static int lib_code = 0;
+static int error_loaded = 0;
-static int GOST_lib_error_code = 0;
-static int GOST_error_init = 1;
-
-void ERR_load_GOST_strings(void)
+int ERR_load_GOST_strings(void)
{
- if (GOST_lib_error_code == 0)
- GOST_lib_error_code = ERR_get_next_error_library();
+ if (lib_code == 0)
+ lib_code = ERR_get_next_error_library();
- if (GOST_error_init) {
- GOST_error_init = 0;
+ if (!error_loaded) {
#ifndef OPENSSL_NO_ERR
- ERR_load_strings(GOST_lib_error_code, GOST_str_functs);
- ERR_load_strings(GOST_lib_error_code, GOST_str_reasons);
-#endif
-
-#ifdef GOST_LIB_NAME
- GOST_lib_name->error = ERR_PACK(GOST_lib_error_code, 0, 0);
- ERR_load_strings(0, GOST_lib_name);
+ ERR_load_strings(lib_code, GOST_str_functs);
+ ERR_load_strings(lib_code, GOST_str_reasons);
#endif
+ error_loaded = 1;
}
+ return 1;
}
void ERR_unload_GOST_strings(void)
{
- if (GOST_error_init == 0) {
+ if (error_loaded) {
#ifndef OPENSSL_NO_ERR
- ERR_unload_strings(GOST_lib_error_code, GOST_str_functs);
- ERR_unload_strings(GOST_lib_error_code, GOST_str_reasons);
-#endif
-
-#ifdef GOST_LIB_NAME
- ERR_unload_strings(0, GOST_lib_name);
+ ERR_unload_strings(lib_code, GOST_str_functs);
+ ERR_unload_strings(lib_code, GOST_str_reasons);
#endif
- GOST_error_init = 1;
+ error_loaded = 0;
}
}
void ERR_GOST_error(int function, int reason, char *file, int line)
{
- if (GOST_lib_error_code == 0)
- GOST_lib_error_code = ERR_get_next_error_library();
- ERR_PUT_error(GOST_lib_error_code, function, reason, file, line);
+ if (lib_code == 0)
+ lib_code = ERR_get_next_error_library();
+ ERR_PUT_error(lib_code, function, reason, file, line);
}
-/* ====================================================================
- * Copyright (c) 2001-2015 The OpenSSL Project. 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. All advertising materials mentioning features or use of this
- * software must display the following acknowledgment:
- * "This product includes software developed by the OpenSSL Project
- * for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
- *
- * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
- * endorse or promote products derived from this software without
- * prior written permission. For written permission, please contact
- * openssl-core@openssl.org.
- *
- * 5. Products derived from this software may not be called "OpenSSL"
- * nor may "OpenSSL" appear in their names without prior written
- * permission of the OpenSSL Project.
- *
- * 6. Redistributions of any form whatsoever must retain the following
- * acknowledgment:
- * "This product includes software developed by the OpenSSL Project
- * for use in the OpenSSL Toolkit (http://www.openssl.org/)"
- *
- * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
- * EXPRESSED 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 OpenSSL PROJECT OR
- * ITS 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.
- * ====================================================================
- *
- * This product includes cryptographic software written by Eric Young
- * (eay@cryptsoft.com). This product includes software written by Tim
- * Hudson (tjh@cryptsoft.com).
+/*
+ * Generated by util/mkerr.pl DO NOT EDIT
+ * Copyright 1995-2018 The OpenSSL Project Authors. All Rights Reserved.
*
+ * Licensed under the OpenSSL license (the "License"). You may not use
+ * this file except in compliance with the License. You can obtain a copy
+ * in the file LICENSE in the source distribution or at
+ * https://www.openssl.org/source/license.html
*/
-#ifndef HEADER_GOST_ERR_H
-# define HEADER_GOST_ERR_H
+#ifndef HEADER_GOSTERR_H
+# define HEADER_GOSTERR_H
+
+# define GOSTerr(f, r) ERR_GOST_error((f), (r), OPENSSL_FILE, OPENSSL_LINE)
+
# ifdef __cplusplus
extern "C" {
# endif
+int ERR_load_GOST_strings(void);
+void ERR_unload_GOST_strings(void);
+void ERR_GOST_error(int function, int reason, char *file, int line);
+# ifdef __cplusplus
+}
+# endif
-/* BEGIN ERROR CODES */
/*
- * The following lines are auto generated by the script mkerr.pl. Any changes
- * made after this point may be overwritten when the script is next run.
+ * GOST function codes.
*/
- void ERR_load_GOST_strings(void);
- void ERR_unload_GOST_strings(void);
- void ERR_GOST_error(int function, int reason, char *file, int line);
-# define GOSTerr(f,r) ERR_GOST_error((f),(r),__FILE__,__LINE__)
-
-/* Error codes for the GOST functions. */
-
-/* Function codes. */
# define GOST_F_DECODE_GOST_ALGOR_PARAMS 100
# define GOST_F_ENCODE_GOST_ALGOR_PARAMS 101
# define GOST_F_FILL_GOST_EC_PARAMS 102
# define GOST_F_GOST_EC_KEYGEN 108
# define GOST_F_GOST_EC_SIGN 109
# define GOST_F_GOST_EC_VERIFY 110
-# define GOST_F_GOST_IMIT_CTRL 111
-# define GOST_F_GOST_IMIT_FINAL 112
-# define GOST_F_GOST_IMIT_UPDATE 113
-# define GOST_F_PARAM_COPY_GOST_EC 114
-# define GOST_F_PKEY_GOST01_PARAMGEN 115
-# define GOST_F_PKEY_GOST12_PARAMGEN 116
-# define GOST_F_PKEY_GOST_CTRL 117
-# define GOST_F_PKEY_GOST_ECCP_DECRYPT 118
-# define GOST_F_PKEY_GOST_ECCP_ENCRYPT 119
-# define GOST_F_PKEY_GOST_EC_CTRL_STR_256 120
-# define GOST_F_PKEY_GOST_EC_CTRL_STR_512 121
-# define GOST_F_PKEY_GOST_EC_DERIVE 122
-# define GOST_F_PKEY_GOST_MAC_CTRL 123
-# define GOST_F_PKEY_GOST_MAC_CTRL_STR 124
-# define GOST_F_PKEY_GOST_MAC_KEYGEN 125
-# define GOST_F_PKEY_GOST_MAC_SIGNCTX_INIT 132
-# define GOST_F_PRINT_GOST_EC_PUB 126
-# define GOST_F_PRIV_DECODE_GOST 127
-# define GOST_F_PUB_DECODE_GOST_EC 128
-# define GOST_F_PUB_ENCODE_GOST_EC 129
-# define GOST_F_UNPACK_CP_SIGNATURE 130
-# define GOST_F_VKO_COMPUTE_KEY 131
+# define GOST_F_GOST_GRASSHOPPER_CIPHER_CTL 111
+# define GOST_F_GOST_GRASSHOPPER_SET_ASN1_PARAMETERS 112
+# define GOST_F_GOST_IMIT_CTRL 113
+# define GOST_F_GOST_IMIT_FINAL 114
+# define GOST_F_GOST_IMIT_UPDATE 115
+# define GOST_F_OMAC_IMIT_CTRL 116
+# define GOST_F_OMAC_IMIT_FINAL 117
+# define GOST_F_OMAC_IMIT_UPDATE 118
+# define GOST_F_OMAC_KEY 138
+# define GOST_F_PARAM_COPY_GOST_EC 119
+# define GOST_F_PKEY_GOST2001_PARAMGEN 120
+# define GOST_F_PKEY_GOST2012_PARAMGEN 121
+# define GOST_F_PKEY_GOST_CTRL 122
+# define GOST_F_PKEY_GOST_ECCP_DECRYPT 123
+# define GOST_F_PKEY_GOST_ECCP_ENCRYPT 124
+# define GOST_F_PKEY_GOST_EC_CTRL_STR_256 125
+# define GOST_F_PKEY_GOST_EC_CTRL_STR_512 126
+# define GOST_F_PKEY_GOST_EC_DERIVE 127
+# define GOST_F_PKEY_GOST_GRASSHOPPER_MAC_SIGNCTX_INIT 141
+# define GOST_F_PKEY_GOST_MAC_CTRL 128
+# define GOST_F_PKEY_GOST_MAC_CTRL_STR 129
+# define GOST_F_PKEY_GOST_MAC_KEYGEN_BASE 130
+# define GOST_F_PKEY_GOST_MAC_SIGNCTX_INIT 131
+# define GOST_F_PKEY_GOST_MAGMA_MAC_SIGNCTX_INIT 142
+# define GOST_F_PKEY_GOST_OMAC_CTRL 139
+# define GOST_F_PKEY_GOST_OMAC_CTRL_STR 140
+# define GOST_F_PRINT_GOST_EC_PUB 132
+# define GOST_F_PRIV_DECODE_GOST 133
+# define GOST_F_PUB_DECODE_GOST_EC 134
+# define GOST_F_PUB_ENCODE_GOST_EC 135
+# define GOST_F_UNPACK_CP_SIGNATURE 136
+# define GOST_F_VKO_COMPUTE_KEY 137
-/* Reason codes. */
+/*
+ * GOST reason codes.
+ */
# define GOST_R_BAD_KEY_PARAMETERS_FORMAT 100
+# define GOST_R_BAD_ORDER 132
# define GOST_R_BAD_PKEY_PARAMETERS_FORMAT 101
# define GOST_R_CANNOT_PACK_EPHEMERAL_KEY 102
-# define GOST_R_CTRL_CALL_FAILED 103
-# define GOST_R_ERROR_COMPUTING_SHARED_KEY 104
-# define GOST_R_ERROR_PARSING_KEY_TRANSPORT_INFO 105
-# define GOST_R_ERROR_POINT_MUL 106
-# define GOST_R_INCOMPATIBLE_ALGORITHMS 107
-# define GOST_R_INCOMPATIBLE_PEER_KEY 108
-# define GOST_R_INVALID_CIPHER_PARAMS 109
-# define GOST_R_INVALID_CIPHER_PARAM_OID 110
-# define GOST_R_INVALID_DIGEST_TYPE 111
-# define GOST_R_INVALID_IV_LENGTH 112
-# define GOST_R_INVALID_MAC_KEY_LENGTH 113
-# define GOST_R_INVALID_MAC_KEY_SIZE 128
-# define GOST_R_INVALID_MAC_PARAMS 130
-# define GOST_R_INVALID_MAC_SIZE 129
-# define GOST_R_INVALID_PARAMSET 114
-# define GOST_R_KEY_IS_NOT_INITIALIZED 115
-# define GOST_R_KEY_PARAMETERS_MISSING 116
-# define GOST_R_MAC_KEY_NOT_SET 117
-# define GOST_R_NO_PARAMETERS_SET 118
-# define GOST_R_NO_PEER_KEY 119
-# define GOST_R_NO_PRIVATE_PART_OF_NON_EPHEMERAL_KEYPAIR 120
-# define GOST_R_PUBLIC_KEY_UNDEFINED 121
-# define GOST_R_RNG_ERROR 122
-# define GOST_R_SIGNATURE_MISMATCH 123
-# define GOST_R_SIGNATURE_PARTS_GREATER_THAN_Q 124
-# define GOST_R_UKM_NOT_SET 125
-# define GOST_R_UNSUPPORTED_CIPHER_CTL_COMMAND 126
-# define GOST_R_UNSUPPORTED_PARAMETER_SET 127
+# define GOST_R_CIPHER_NOT_FOUND 103
+# define GOST_R_CTRL_CALL_FAILED 104
+# define GOST_R_ERROR_COMPUTING_SHARED_KEY 105
+# define GOST_R_ERROR_PARSING_KEY_TRANSPORT_INFO 106
+# define GOST_R_ERROR_POINT_MUL 107
+# define GOST_R_INCOMPATIBLE_ALGORITHMS 108
+# define GOST_R_INCOMPATIBLE_PEER_KEY 109
+# define GOST_R_INVALID_CIPHER_PARAMS 110
+# define GOST_R_INVALID_CIPHER_PARAM_OID 111
+# define GOST_R_INVALID_DIGEST_TYPE 112
+# define GOST_R_INVALID_IV_LENGTH 113
+# define GOST_R_INVALID_MAC_KEY_LENGTH 114
+# define GOST_R_INVALID_MAC_KEY_SIZE 115
+# define GOST_R_INVALID_MAC_PARAMS 116
+# define GOST_R_INVALID_MAC_SIZE 117
+# define GOST_R_INVALID_PARAMSET 118
+# define GOST_R_KEY_IS_NOT_INITIALIZED 119
+# define GOST_R_KEY_PARAMETERS_MISSING 120
+# define GOST_R_MAC_KEY_NOT_SET 121
+# define GOST_R_NO_PARAMETERS_SET 122
+# define GOST_R_NO_PEER_KEY 123
+# define GOST_R_NO_PRIVATE_PART_OF_NON_EPHEMERAL_KEYPAIR 124
+# define GOST_R_PUBLIC_KEY_UNDEFINED 125
+# define GOST_R_RNG_ERROR 126
+# define GOST_R_SIGNATURE_MISMATCH 127
+# define GOST_R_SIGNATURE_PARTS_GREATER_THAN_Q 128
+# define GOST_R_UKM_NOT_SET 129
+# define GOST_R_UNSUPPORTED_CIPHER_CTL_COMMAND 130
+# define GOST_R_UNSUPPORTED_PARAMETER_SET 131
-# ifdef __cplusplus
-}
-# endif
#endif
--- /dev/null
+openssl dgst -mac magma-mac -macopt hexkey:ffeeddccbbaa99887766554433221100f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff magma.dat
+154e7210
+
+openssl dgst -mac grasshopper-mac -macopt hexkey:8899aabbccddeeff0011223344556677fedcba98765432100123456789abcdef gh.dat
+336f4d296059fbe3
--- /dev/null
+\92Þðk<\13
+YÛTÇ\ 4ø\18\9d J\98û.g¨\ 2L\89\12@\9b\17µ~A
\ No newline at end of file
L GOST e_gost_err.h e_gost_err.c
-L NONE asymm.h NONE
-L NONE md.h NONE
-L NONE crypt.h NONE
-L NONE gostkeyx.h NONE
--- /dev/null
+# Copyright 1999-2018 The OpenSSL Project Authors. All Rights Reserved.
+#
+# Licensed under the OpenSSL license (the "License"). You may not use
+# this file except in compliance with the License. You can obtain a copy
+# in the file LICENSE in the source distribution or at
+# https://www.openssl.org/source/license.html
+
+# Function codes
+GOST_F_DECODE_GOST_ALGOR_PARAMS:100:decode_gost_algor_params
+GOST_F_ENCODE_GOST_ALGOR_PARAMS:101:encode_gost_algor_params
+GOST_F_FILL_GOST_EC_PARAMS:102:fill_GOST_EC_params
+GOST_F_GET_ENCRYPTION_PARAMS:103:get_encryption_params
+GOST_F_GOST89_GET_ASN1_PARAMETERS:104:gost89_get_asn1_parameters
+GOST_F_GOST89_SET_ASN1_PARAMETERS:105:gost89_set_asn1_parameters
+GOST_F_GOST_CIPHER_CTL:106:gost_cipher_ctl
+GOST_F_GOST_EC_COMPUTE_PUBLIC:107:gost_ec_compute_public
+GOST_F_GOST_EC_KEYGEN:108:gost_ec_keygen
+GOST_F_GOST_EC_SIGN:109:gost_ec_sign
+GOST_F_GOST_EC_VERIFY:110:gost_ec_verify
+GOST_F_GOST_GRASSHOPPER_CIPHER_CTL:111:gost_grasshopper_cipher_ctl
+GOST_F_GOST_GRASSHOPPER_SET_ASN1_PARAMETERS:112:\
+ gost_grasshopper_set_asn1_parameters
+GOST_F_GOST_IMIT_CTRL:113:gost_imit_ctrl
+GOST_F_GOST_IMIT_FINAL:114:gost_imit_final
+GOST_F_GOST_IMIT_UPDATE:115:gost_imit_update
+GOST_F_OMAC_IMIT_CTRL:116:omac_imit_ctrl
+GOST_F_OMAC_IMIT_FINAL:117:omac_imit_final
+GOST_F_OMAC_IMIT_UPDATE:118:omac_imit_update
+GOST_F_OMAC_KEY:138:omac_key
+GOST_F_PARAM_COPY_GOST_EC:119:param_copy_gost_ec
+GOST_F_PKEY_GOST2001_PARAMGEN:120:pkey_gost2001_paramgen
+GOST_F_PKEY_GOST2012_PARAMGEN:121:pkey_gost2012_paramgen
+GOST_F_PKEY_GOST_CTRL:122:pkey_gost_ctrl
+GOST_F_PKEY_GOST_ECCP_DECRYPT:123:pkey_GOST_ECcp_decrypt
+GOST_F_PKEY_GOST_ECCP_ENCRYPT:124:pkey_GOST_ECcp_encrypt
+GOST_F_PKEY_GOST_EC_CTRL_STR_256:125:pkey_gost_ec_ctrl_str_256
+GOST_F_PKEY_GOST_EC_CTRL_STR_512:126:pkey_gost_ec_ctrl_str_512
+GOST_F_PKEY_GOST_EC_DERIVE:127:pkey_gost_ec_derive
+GOST_F_PKEY_GOST_GRASSHOPPER_MAC_SIGNCTX_INIT:141:\
+ pkey_gost_grasshopper_mac_signctx_init
+GOST_F_PKEY_GOST_MAC_CTRL:128:pkey_gost_mac_ctrl
+GOST_F_PKEY_GOST_MAC_CTRL_STR:129:pkey_gost_mac_ctrl_str
+GOST_F_PKEY_GOST_MAC_KEYGEN_BASE:130:pkey_gost_mac_keygen_base
+GOST_F_PKEY_GOST_MAC_SIGNCTX_INIT:131:pkey_gost_mac_signctx_init
+GOST_F_PKEY_GOST_MAGMA_MAC_SIGNCTX_INIT:142:pkey_gost_magma_mac_signctx_init
+GOST_F_PKEY_GOST_OMAC_CTRL:139:pkey_gost_omac_ctrl
+GOST_F_PKEY_GOST_OMAC_CTRL_STR:140:pkey_gost_omac_ctrl_str
+GOST_F_PRINT_GOST_EC_PUB:132:print_gost_ec_pub
+GOST_F_PRIV_DECODE_GOST:133:priv_decode_gost
+GOST_F_PUB_DECODE_GOST_EC:134:pub_decode_gost_ec
+GOST_F_PUB_ENCODE_GOST_EC:135:pub_encode_gost_ec
+GOST_F_UNPACK_CP_SIGNATURE:136:unpack_cp_signature
+GOST_F_VKO_COMPUTE_KEY:137:VKO_compute_key
+
+#Reason codes
+GOST_R_BAD_KEY_PARAMETERS_FORMAT:100:bad key parameters format
+GOST_R_BAD_ORDER:132:bad order
+GOST_R_BAD_PKEY_PARAMETERS_FORMAT:101:bad pkey parameters format
+GOST_R_CANNOT_PACK_EPHEMERAL_KEY:102:cannot pack ephemeral key
+GOST_R_CIPHER_NOT_FOUND:103:cipher not found
+GOST_R_CTRL_CALL_FAILED:104:ctrl call failed
+GOST_R_ERROR_COMPUTING_SHARED_KEY:105:error computing shared key
+GOST_R_ERROR_PARSING_KEY_TRANSPORT_INFO:106:error parsing key transport info
+GOST_R_ERROR_POINT_MUL:107:error point mul
+GOST_R_INCOMPATIBLE_ALGORITHMS:108:incompatible algorithms
+GOST_R_INCOMPATIBLE_PEER_KEY:109:incompatible peer key
+GOST_R_INVALID_CIPHER_PARAMS:110:invalid cipher params
+GOST_R_INVALID_CIPHER_PARAM_OID:111:invalid cipher param oid
+GOST_R_INVALID_DIGEST_TYPE:112:invalid digest type
+GOST_R_INVALID_IV_LENGTH:113:invalid iv length
+GOST_R_INVALID_MAC_KEY_LENGTH:114:invalid mac key length
+GOST_R_INVALID_MAC_KEY_SIZE:115:invalid mac key size
+GOST_R_INVALID_MAC_PARAMS:116:invalid mac params
+GOST_R_INVALID_MAC_SIZE:117:invalid mac size
+GOST_R_INVALID_PARAMSET:118:invalid paramset
+GOST_R_KEY_IS_NOT_INITIALIZED:119:key is not initialized
+GOST_R_KEY_PARAMETERS_MISSING:120:key parameters missing
+GOST_R_MAC_KEY_NOT_SET:121:mac key not set
+GOST_R_NO_PARAMETERS_SET:122:no parameters set
+GOST_R_NO_PEER_KEY:123:no peer key
+GOST_R_NO_PRIVATE_PART_OF_NON_EPHEMERAL_KEYPAIR:124:\
+ no private part of non ephemeral keypair
+GOST_R_PUBLIC_KEY_UNDEFINED:125:public key undefined
+GOST_R_RNG_ERROR:126:rng error
+GOST_R_SIGNATURE_MISMATCH:127:signature mismatch
+GOST_R_SIGNATURE_PARTS_GREATER_THAN_Q:128:signature parts greater than q
+GOST_R_UKM_NOT_SET:129:ukm not set
+GOST_R_UNSUPPORTED_CIPHER_CTL_COMMAND:130:unsupported cipher ctl command
+GOST_R_UNSUPPORTED_PARAMETER_SET:131:unsupported parameter set
0xC0, 0x86, 0xDC, 0xC2, 0xEF, 0x4C, 0xA9, 0x2B
};
+const byte ACPKM_D_const[] = {
+ 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
+ 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F,
+ 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
+ 0x98, 0x99, 0x9A, 0x9B, 0x9C, 0x9D, 0x9E, 0x9F,
+};
+
/* Initialization of gost_ctx subst blocks*/
static void kboxinit(gost_ctx * c, const gost_subst_block * b)
{
gostcrypt(c, inblock, outblock);
}
-/* Set 256 bit key into context */
+/* Set 256 bit gost89 key into context */
void gost_key(gost_ctx * c, const byte * k)
{
int i, j;
}
}
-/* Retrieve 256-bit key from context */
+/* Set 256 bit Magma key into context */
+void magma_key(gost_ctx * c, const byte * k)
+{
+ int i, j;
+ for (i = 0, j = 0; i < 8; i++, j += 4) {
+ c->k[i] =
+ k[j+3] | (k[j + 2] << 8) | (k[j + 1] << 16) | ((word32) k[j] <<
+ 24);
+ }
+}
+
+/* Retrieve 256-bit gost89 key from context */
void gost_get_key(gost_ctx * c, byte * k)
{
int i, j;
}
}
+/* Retrieve 256-bit magma key from context */
+void magma_get_key(gost_ctx * c, byte * k)
+{
+ int i, j;
+ for (i = 0, j = 0; i < 8; i++, j += 4) {
+ k[j + 3] = (byte) (c->k[i] & 0xFF);
+ k[j + 2] = (byte) ((c->k[i] >> 8) & 0xFF);
+ k[j + 1] = (byte) ((c->k[i] >> 16) & 0xFF);
+ k[j + 0] = (byte) ((c->k[i] >> 24) & 0xFF);
+ }
+}
+
/* Initalize context. Provides default value for subst_block */
void gost_init(gost_ctx * c, const gost_subst_block * b)
{
gostcrypt(ctx, iv, newiv);
memcpy(iv, newiv, 8);
}
+
+void acpkm_magma_key_meshing(gost_ctx *ctx)
+{
+ unsigned char newkey[32];
+ int i, j;
+ unsigned char buf[8], keybuf[8];
+
+ for (i = 0; i < 4; i++)
+ {
+ for (j = 0; j < 8; j++)
+ {
+ buf[j] = ACPKM_D_const[8*i + 7-j];
+ }
+ gostcrypt(ctx, buf, keybuf);
+ memcpy(newkey+8*i, keybuf+4, 4);
+ memcpy(newkey+8*i+4, keybuf, 4);
+ }
+ /* set new key */
+ gost_key(ctx, newkey);
+}
+
+#ifdef ENABLE_UNIT_TESTS
+#include <stdio.h>
+#include <string.h>
+
+static void hexdump(FILE *f, const char *title, const unsigned char *s, int l)
+{
+ int n = 0;
+
+ fprintf(f, "%s", title);
+ for (; n < l; ++n) {
+ if ((n % 16) == 0)
+ fprintf(f, "\n%04x", n);
+ fprintf(f, " %02x", s[n]);
+ }
+ fprintf(f, "\n");
+}
+
+int main(void)
+{
+ const unsigned char initial_key[] = {
+ 0x88, 0x99, 0xAA, 0xBB, 0xCC, 0xDD, 0xEE, 0xFF,
+ 0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77,
+ 0xFE, 0xDC, 0xBA, 0x98, 0x76, 0x54, 0x32, 0x10,
+ 0x01, 0x23, 0x45, 0x67, 0x89, 0xAB, 0xCD, 0xEF
+ };
+
+ const unsigned char meshed_key[] = {
+ 0x86, 0x3E, 0xA0, 0x17, 0x84, 0x2C, 0x3D, 0x37,
+ 0x2B, 0x18, 0xA8, 0x5A, 0x28, 0xE2, 0x31, 0x7D,
+ 0x74, 0xBE, 0xFC, 0x10, 0x77, 0x20, 0xDE, 0x0C,
+ 0x9E, 0x8A, 0xB9, 0x74, 0xAB, 0xD0, 0x0C, 0xA0,
+ };
+
+ unsigned char buf[32];
+
+ gost_ctx ctx;
+ kboxinit(&ctx, &Gost28147_TC26ParamSetZ);
+ magma_key(&ctx, initial_key);
+ magma_get_key(&ctx, buf);
+
+ hexdump(stdout, "Initial key", buf, 32);
+
+ acpkm_magma_key_meshing(&ctx);
+ magma_get_key(&ctx, buf);
+ hexdump(stdout, "Meshed key - K2", buf, 32);
+
+ if (memcmp(meshed_key, buf, 32))
+ {
+ fprintf(stderr, "Magma meshing failed");
+ }
+
+ acpkm_magma_key_meshing(&ctx);
+ magma_get_key(&ctx, buf);
+ hexdump(stdout, "Meshed key - K3", buf, 32);
+
+ acpkm_magma_key_meshing(&ctx);
+ magma_get_key(&ctx, buf);
+ hexdump(stdout, "Meshed key - K4", buf, 32);
+
+}
+
+#endif
void gostdecrypt(gost_ctx * c, const byte * in, byte * out);
/* Set key into context */
void gost_key(gost_ctx * ctx, const byte * key);
+/* Set key into context */
+void magma_key(gost_ctx * ctx, const byte * key);
/* Get key from context */
void gost_get_key(gost_ctx * ctx, byte * key);
/* Set S-blocks into context */
return -2;
}
+static int mac_ctrl_magma(EVP_PKEY *pkey, int op, long arg1, void *arg2)
+{
+ switch (op) {
+ case ASN1_PKEY_CTRL_DEFAULT_MD_NID:
+ if (arg2) {
+ *(int *)arg2 = NID_magma_mac;
+ return 2;
+ }
+ }
+ return -2;
+}
+
+static int mac_ctrl_grasshopper(EVP_PKEY *pkey, int op, long arg1, void *arg2)
+{
+ switch (op) {
+ case ASN1_PKEY_CTRL_DEFAULT_MD_NID:
+ if (arg2) {
+ *(int *)arg2 = NID_grasshopper_mac;
+ return 2;
+ }
+ }
+ return -2;
+}
+
static int gost2001_param_encode(const EVP_PKEY *pkey, unsigned char **pder)
{
int nid =
EVP_PKEY_asn1_set_free(*ameth, mackey_free_gost);
EVP_PKEY_asn1_set_ctrl(*ameth, mac_ctrl_gost_12);
break;
+ case NID_magma_mac:
+ EVP_PKEY_asn1_set_free(*ameth, mackey_free_gost);
+ EVP_PKEY_asn1_set_ctrl(*ameth, mac_ctrl_magma);
+ break;
+ case NID_grasshopper_mac:
+ EVP_PKEY_asn1_set_free(*ameth, mackey_free_gost);
+ EVP_PKEY_asn1_set_ctrl(*ameth, mac_ctrl_grasshopper);
+ break;
}
return 1;
}
/* Control function */
static int gost_cipher_ctl(EVP_CIPHER_CTX *ctx, int type, int arg, void *ptr);
+static int magma_cipher_init(EVP_CIPHER_CTX *ctx, const unsigned char *key,
+ const unsigned char *iv, int enc);
+/* Handles block of data in CBC mode */
+static int magma_cipher_do_cbc(EVP_CIPHER_CTX *ctx, unsigned char *out,
+ const unsigned char *in, size_t inl);
+static int magma_cipher_do_ctr(EVP_CIPHER_CTX *ctx, unsigned char *out,
+ const unsigned char *in, size_t inl);
+
static EVP_CIPHER *_hidden_Gost28147_89_cipher = NULL;
const EVP_CIPHER *cipher_gost(void)
{
return _hidden_gost89_cnt_12;
}
+static EVP_CIPHER *_hidden_magma_ctr = NULL;
+const EVP_CIPHER *cipher_magma_ctr(void)
+{
+ if (_hidden_magma_ctr == NULL
+ && ((_hidden_magma_ctr =
+ EVP_CIPHER_meth_new(NID_magma_ctr, 1 /* block_size */ ,
+ 32 /* key_size */ )) == NULL
+ || !EVP_CIPHER_meth_set_iv_length(_hidden_magma_ctr, 8)
+ || !EVP_CIPHER_meth_set_flags(_hidden_magma_ctr,
+ EVP_CIPH_CTR_MODE |
+ EVP_CIPH_NO_PADDING |
+ EVP_CIPH_CUSTOM_IV |
+ EVP_CIPH_RAND_KEY |
+ EVP_CIPH_ALWAYS_CALL_INIT)
+ || !EVP_CIPHER_meth_set_init(_hidden_magma_ctr,
+ magma_cipher_init)
+ || !EVP_CIPHER_meth_set_do_cipher(_hidden_magma_ctr,
+ magma_cipher_do_ctr)
+ || !EVP_CIPHER_meth_set_cleanup(_hidden_magma_ctr,
+ gost_cipher_cleanup)
+ || !EVP_CIPHER_meth_set_impl_ctx_size(_hidden_magma_ctr,
+ sizeof(struct
+ ossl_gost_cipher_ctx))
+ || !EVP_CIPHER_meth_set_set_asn1_params(_hidden_magma_ctr,
+ gost89_set_asn1_parameters)
+ || !EVP_CIPHER_meth_set_get_asn1_params(_hidden_magma_ctr,
+ gost89_get_asn1_parameters)
+ || !EVP_CIPHER_meth_set_ctrl(_hidden_magma_ctr,
+ gost_cipher_ctl))) {
+ EVP_CIPHER_meth_free(_hidden_magma_ctr);
+ _hidden_magma_ctr = NULL;
+ }
+ return _hidden_magma_ctr;
+}
+
+static EVP_CIPHER *_hidden_magma_cbc = NULL;
+const EVP_CIPHER *cipher_magma_cbc(void)
+{
+ if (_hidden_magma_cbc == NULL
+ && ((_hidden_magma_cbc =
+ EVP_CIPHER_meth_new(NID_magma_cbc, 8 /* block_size */ ,
+ 32 /* key_size */ )) == NULL
+ || !EVP_CIPHER_meth_set_iv_length(_hidden_magma_cbc, 8)
+ || !EVP_CIPHER_meth_set_flags(_hidden_magma_cbc,
+ EVP_CIPH_CBC_MODE |
+ EVP_CIPH_CUSTOM_IV |
+ EVP_CIPH_RAND_KEY |
+ EVP_CIPH_ALWAYS_CALL_INIT)
+ || !EVP_CIPHER_meth_set_init(_hidden_magma_cbc,
+ magma_cipher_init)
+ || !EVP_CIPHER_meth_set_do_cipher(_hidden_magma_cbc,
+ magma_cipher_do_cbc)
+ || !EVP_CIPHER_meth_set_cleanup(_hidden_magma_cbc,
+ gost_cipher_cleanup)
+ || !EVP_CIPHER_meth_set_impl_ctx_size(_hidden_magma_cbc,
+ sizeof(struct
+ ossl_gost_cipher_ctx))
+ || !EVP_CIPHER_meth_set_set_asn1_params(_hidden_magma_cbc,
+ gost89_set_asn1_parameters)
+ || !EVP_CIPHER_meth_set_get_asn1_params(_hidden_magma_cbc,
+ gost89_get_asn1_parameters)
+ || !EVP_CIPHER_meth_set_ctrl(_hidden_magma_cbc,
+ gost_cipher_ctl))) {
+ EVP_CIPHER_meth_free(_hidden_magma_cbc);
+ _hidden_magma_cbc = NULL;
+ }
+ return _hidden_magma_cbc;
+}
+
void cipher_gost_destroy(void)
{
EVP_CIPHER_meth_free(_hidden_Gost28147_89_cipher);
_hidden_Gost28147_89_cbc = NULL;
EVP_CIPHER_meth_free(_hidden_gost89_cnt_12);
_hidden_gost89_cnt_12 = NULL;
+ EVP_CIPHER_meth_free(_hidden_magma_cbc);
+ _hidden_magma_cbc = NULL;
+ EVP_CIPHER_meth_free(_hidden_magma_ctr);
+ _hidden_magma_ctr = NULL;
}
/* Implementation of GOST 28147-89 in MAC (imitovstavka) mode */
return 1;
}
+static int magma_cipher_init_param(EVP_CIPHER_CTX *ctx,
+ const unsigned char *key,
+ const unsigned char *iv, int enc,
+ int paramNID, int mode)
+{
+ struct ossl_gost_cipher_ctx *c = EVP_CIPHER_CTX_get_cipher_data(ctx);
+ if (EVP_CIPHER_CTX_get_app_data(ctx) == NULL) {
+ if (!gost_cipher_set_param(c, NID_id_tc26_gost_28147_param_Z))
+ return 0;
+ EVP_CIPHER_CTX_set_app_data(ctx, EVP_CIPHER_CTX_get_cipher_data(ctx));
+ }
+ if (key)
+ magma_key(&(c->cctx), key);
+ if (iv) {
+ memcpy((unsigned char *)EVP_CIPHER_CTX_original_iv(ctx), iv,
+ EVP_CIPHER_CTX_iv_length(ctx));
+ }
+ memcpy(EVP_CIPHER_CTX_iv_noconst(ctx),
+ EVP_CIPHER_CTX_original_iv(ctx), EVP_CIPHER_CTX_iv_length(ctx));
+ return 1;
+}
+
static int gost_cipher_init_cnt(EVP_CIPHER_CTX *ctx,
const unsigned char *key,
const unsigned char *iv,
EVP_CIPH_CBC_MODE);
}
+/* Initializes EVP_CIPHER_CTX with default values */
+int magma_cipher_init(EVP_CIPHER_CTX *ctx, const unsigned char *key,
+ const unsigned char *iv, int enc)
+{
+ return magma_cipher_init_param(ctx, key, iv, enc, NID_undef,
+ EVP_CIPH_CBC_MODE);
+}
+
/*
* Wrapper around gostcrypt function from gost89.c which perform key meshing
* when nesseccary
c->count = c->count % 1024 + 8;
}
-/* GOST encryptoon in CBC mode */
+/* GOST encryption in CBC mode */
int gost_cipher_do_cbc(EVP_CIPHER_CTX *ctx, unsigned char *out,
const unsigned char *in, size_t inl)
{
return 1;
}
+/* MAGMA encryption in CBC mode */
+int magma_cipher_do_cbc(EVP_CIPHER_CTX *ctx, unsigned char *out,
+ const unsigned char *in, size_t inl)
+{
+ unsigned char b[8];
+ unsigned char d[8];
+ const unsigned char *in_ptr = in;
+ unsigned char *out_ptr = out;
+ int i;
+ struct ossl_gost_cipher_ctx *c = EVP_CIPHER_CTX_get_cipher_data(ctx);
+ unsigned char *iv = EVP_CIPHER_CTX_iv_noconst(ctx);
+ if (EVP_CIPHER_CTX_encrypting(ctx)) {
+ while (inl > 0) {
+
+ for (i = 0; i < 8; i++) {
+ b[7-i] = iv[i] ^ in_ptr[i];
+ }
+ gostcrypt(&(c->cctx), b, d);
+
+ for (i = 0; i < 8; i++) {
+ out_ptr[7-i] = d[i];
+ }
+ memcpy(iv, out_ptr, 8);
+ out_ptr += 8;
+ in_ptr += 8;
+ inl -= 8;
+ }
+ } else {
+ while (inl > 0) {
+ for (i = 0; i < 8; i++) {
+ d[7-i] = in_ptr[i];
+ }
+ gostdecrypt(&(c->cctx), d, b);
+ for (i = 0; i < 8; i++) {
+ out_ptr[i] = iv[i] ^ b[7-i];
+ }
+ memcpy(iv, in_ptr, 8);
+ out_ptr += 8;
+ in_ptr += 8;
+ inl -= 8;
+ }
+ }
+ return 1;
+}
+
+/* increment counter (64-bit int) by 1 */
+static void ctr64_inc(unsigned char *counter)
+{
+ inc_counter(counter, 8);
+}
+
+/* MAGMA encryption in CTR mode */
+static int magma_cipher_do_ctr(EVP_CIPHER_CTX *ctx, unsigned char *out,
+ const unsigned char *in, size_t inl)
+{
+ const unsigned char *in_ptr = in;
+ unsigned char *out_ptr = out;
+ size_t i = 0;
+ size_t j;
+ struct ossl_gost_cipher_ctx *c = EVP_CIPHER_CTX_get_cipher_data(ctx);
+ unsigned char *buf = EVP_CIPHER_CTX_buf_noconst(ctx);
+ unsigned char *iv = EVP_CIPHER_CTX_iv_noconst(ctx);
+ unsigned char b[8];
+/* Process partial blocks */
+ if (EVP_CIPHER_CTX_num(ctx)) {
+ for (j = EVP_CIPHER_CTX_num(ctx), i = 0; j < 8 && i < inl;
+ j++, i++, in_ptr++, out_ptr++) {
+ *out_ptr = buf[7-j] ^ (*in_ptr);
+ }
+ if (j == 8) {
+ EVP_CIPHER_CTX_set_num(ctx, 0);
+ } else {
+ EVP_CIPHER_CTX_set_num(ctx, j);
+ return 1;
+ }
+ }
+
+/* Process full blocks */
+ for (; i + 8 <= inl; i += 8, in_ptr += 8, out_ptr += 8) {
+ for (j = 0; j < 8; j++) {
+ b[7-j] = iv[j];
+ }
+ gostcrypt(&(c->cctx), b, buf);
+ for (j = 0; j < 8; j++) {
+ out_ptr[j] = buf[7-j] ^ in_ptr[j];
+ }
+ ctr64_inc(iv);
+ }
+
+/* Process the rest of plaintext */
+ if (i < inl) {
+ for (j = 0; j < 8; j++) {
+ b[7-j] = iv[j];
+ }
+ gostcrypt(&(c->cctx), iv, buf);
+ ctr64_inc(iv);
+ for (j = 0; i < inl; j++, i++) {
+ out_ptr[j] = buf[7-j] ^ in_ptr[j];
+ }
+
+ EVP_CIPHER_CTX_set_num(ctx, j);
+ } else {
+ EVP_CIPHER_CTX_set_num(ctx, 0);
+ }
+
+ return 1;
+}
+
/* GOST encryption in CFB mode */
int gost_cipher_do_cfb(EVP_CIPHER_CTX *ctx, unsigned char *out,
const unsigned char *in, size_t inl)
NID_grasshopper_cfb,
NID_grasshopper_ofb,
NID_grasshopper_ctr,
+ NID_magma_cbc,
+ NID_magma_ctr,
0
};
static int gost_digest_nids(const int** nids) {
- static int digest_nids[6] = {0, 0, 0, 0, 0, 0};
+ static int digest_nids[8] = {0, 0, 0, 0, 0, 0, 0, 0};
static int pos = 0;
static int init = 0;
digest_nids[pos++] = EVP_MD_type(md);
if ((md = imit_gost_cp_12()) != NULL)
digest_nids[pos++] = EVP_MD_type(md);
+ if ((md = magma_omac()) != NULL)
+ digest_nids[pos++] = EVP_MD_type(md);
+ if ((md = grasshopper_omac()) != NULL)
+ digest_nids[pos++] = EVP_MD_type(md);
+
+
digest_nids[pos] = 0;
init = 1;
}
NID_id_GostR3410_2012_256,
NID_id_GostR3410_2012_512,
NID_gost_mac_12,
+ NID_magma_mac,
+ NID_grasshopper_mac,
0
};
static EVP_PKEY_METHOD* pmeth_GostR3410_2001 = NULL,
* pmeth_GostR3410_2012_256 = NULL,
* pmeth_GostR3410_2012_512 = NULL,
- * pmeth_Gost28147_MAC = NULL, * pmeth_Gost28147_MAC_12 = NULL;
+ * pmeth_Gost28147_MAC = NULL, * pmeth_Gost28147_MAC_12 = NULL,
+ * pmeth_magma_mac = NULL, * pmeth_grasshopper_mac = NULL;
static EVP_PKEY_ASN1_METHOD* ameth_GostR3410_2001 = NULL,
* ameth_GostR3410_2012_256 = NULL,
* ameth_GostR3410_2012_512 = NULL,
- * ameth_Gost28147_MAC = NULL, * ameth_Gost28147_MAC_12 = NULL;
+ * ameth_Gost28147_MAC = NULL, * ameth_Gost28147_MAC_12 = NULL,
+ * ameth_magma_mac = NULL, * ameth_grasshopper_mac = NULL;
static int gost_engine_init(ENGINE* e) {
return 1;
imit_gost_cpa_destroy();
imit_gost_cp_12_destroy();
+ magma_omac_destroy();
+ grasshopper_omac_destroy();
cipher_gost_destroy();
cipher_gost_grasshopper_destroy();
pmeth_GostR3410_2012_256 = NULL;
pmeth_GostR3410_2012_512 = NULL;
pmeth_Gost28147_MAC_12 = NULL;
+ pmeth_magma_mac = NULL;
+ pmeth_grasshopper_mac = NULL;
ameth_GostR3410_2001 = NULL;
ameth_Gost28147_MAC = NULL;
ameth_GostR3410_2012_256 = NULL;
ameth_GostR3410_2012_512 = NULL;
ameth_Gost28147_MAC_12 = NULL;
+ ameth_magma_mac = NULL;
+ ameth_grasshopper_mac = NULL;
ERR_unload_GOST_strings();
"GOST-MAC-12",
"GOST 28147-89 MAC with 2012 params"))
goto end;
+ if (!register_ameth_gost(NID_magma_mac, &ameth_magma_mac,
+ "MAGMA-MAC", "GOST R 34.13-2015 Magma MAC"))
+ goto end;
+ if (!register_ameth_gost(NID_grasshopper_mac, &ameth_grasshopper_mac,
+ "GRASSHOPPER-MAC", "GOST R 34.13-2015 Grasshopper MAC"))
+ goto end;
if (!register_pmeth_gost(NID_id_GostR3410_2001, &pmeth_GostR3410_2001, 0))
goto end;
goto end;
if (!register_pmeth_gost(NID_gost_mac_12, &pmeth_Gost28147_MAC_12, 0))
goto end;
+ if (!register_pmeth_gost(NID_magma_mac, &pmeth_magma_mac, 0))
+ goto end;
+ if (!register_pmeth_gost(NID_grasshopper_mac, &pmeth_grasshopper_mac, 0))
+ goto end;
if (!ENGINE_register_ciphers(e)
|| !ENGINE_register_digests(e)
|| !ENGINE_register_pkey_meths(e)
|| !EVP_add_cipher(cipher_gost_grasshopper_cfb())
|| !EVP_add_cipher(cipher_gost_grasshopper_ofb())
|| !EVP_add_cipher(cipher_gost_grasshopper_ctr())
+ || !EVP_add_cipher(cipher_magma_cbc())
+ || !EVP_add_cipher(cipher_magma_ctr())
|| !EVP_add_digest(digest_gost())
|| !EVP_add_digest(digest_gost2012_512())
|| !EVP_add_digest(digest_gost2012_256())
|| !EVP_add_digest(imit_gost_cpa())
|| !EVP_add_digest(imit_gost_cp_12())
+ || !EVP_add_digest(magma_omac())
+ || !EVP_add_digest(grasshopper_omac())
) {
goto end;
}
*digest = digest_gost2012_512();
} else if (nid == NID_gost_mac_12) {
*digest = imit_gost_cp_12();
+ } else if (nid == NID_magma_mac) {
+ *digest = magma_omac();
+ } else if (nid == NID_grasshopper_mac) {
+ *digest = grasshopper_omac();
} else {
ok = 0;
*digest = NULL;
*cipher = cipher_gost_grasshopper_ofb();
} else if (nid == NID_grasshopper_ctr) {
*cipher = cipher_gost_grasshopper_ctr();
+ } else if (nid == NID_magma_cbc) {
+ *cipher = cipher_magma_cbc();
+ } else if (nid == NID_magma_ctr) {
+ *cipher = cipher_magma_ctr();
} else {
ok = 0;
*cipher = NULL;
case NID_gost_mac_12:
*pmeth = pmeth_Gost28147_MAC_12;
return 1;
+ case NID_magma_mac:
+ *pmeth = pmeth_magma_mac;
+ return 1;
+ case NID_grasshopper_mac:
+ *pmeth = pmeth_grasshopper_mac;
+ return 1;
default:;
}
case NID_gost_mac_12:
*ameth = ameth_Gost28147_MAC_12;
return 1;
+ case NID_magma_mac:
+ *ameth = ameth_magma_mac;
+ return 1;
+ case NID_grasshopper_mac:
+ *ameth = ameth_grasshopper_mac;
+ return 1;
default:;
}
#include <openssl/err.h>
#include <string.h>
+#include "gost_lcl.h"
#include "e_gost_err.h"
enum GRASSHOPPER_CIPHER_TYPE {
return 1;
}
-/* increment counter (128-bit int) by 1 */
-static void ctr128_inc(unsigned char *counter)
+void inc_counter(unsigned char* counter, size_t counter_bytes)
{
- unsigned int n = 16;
unsigned char c;
+ unsigned int n = counter_bytes;
do {
--n;
} while (n);
}
+/* increment counter (128-bit int) by 1 */
+static void ctr128_inc(unsigned char *counter)
+{
+ inc_counter(counter, 16);
+}
+
int gost_grasshopper_cipher_do_ctr(EVP_CIPHER_CTX* ctx, unsigned char* out,
const unsigned char* in, size_t inl) {
gost_grasshopper_cipher_ctx_ctr* c = (gost_grasshopper_cipher_ctx_ctr*) EVP_CIPHER_CTX_get_cipher_data(ctx);
if (!os || !ASN1_OCTET_STRING_set(os, buf, len)) {
OPENSSL_free(buf);
- GOSTerr(GOST_F_GOST89_SET_ASN1_PARAMETERS, ERR_R_MALLOC_FAILURE);
+ GOSTerr(GOST_F_GOST_GRASSHOPPER_SET_ASN1_PARAMETERS, ERR_R_MALLOC_FAILURE);
return 0;
}
OPENSSL_free(buf);
switch (type) {
case EVP_CTRL_RAND_KEY: {
if (RAND_bytes((unsigned char*) ptr, EVP_CIPHER_CTX_key_length(ctx)) <= 0) {
- GOSTerr(GOST_F_GOST_CIPHER_CTL, GOST_R_RNG_ERROR);
+ GOSTerr(GOST_F_GOST_GRASSHOPPER_CIPHER_CTL, GOST_R_RNG_ERROR);
return -1;
}
break;
}
default:
- GOSTerr(GOST_F_GOST_CIPHER_CTL, GOST_R_UNSUPPORTED_CIPHER_CTL_COMMAND);
+ GOSTerr(GOST_F_GOST_GRASSHOPPER_CIPHER_CTL, GOST_R_UNSUPPORTED_CIPHER_CTL_COMMAND);
return -1;
}
return 1;
void imit_gost_cpa_destroy(void);
EVP_MD *imit_gost_cp_12(void);
void imit_gost_cp_12_destroy(void);
+EVP_MD *magma_omac(void);
+void magma_omac_destroy(void);
+EVP_MD *grasshopper_omac(void);
+void grasshopper_omac_destroy(void);
/* Cipher context used for EVP_CIPHER operation */
struct ossl_gost_cipher_ctx {
int paramNID;
const EVP_CIPHER *cipher_gost_cbc();
const EVP_CIPHER *cipher_gost_cpacnt();
const EVP_CIPHER *cipher_gost_cpcnt_12();
+const EVP_CIPHER *cipher_magma_cbc();
+const EVP_CIPHER *cipher_magma_ctr();
void cipher_gost_destroy();
+
+void inc_counter(unsigned char* buffer, size_t buf_len);
+
# define EVP_MD_CTRL_KEY_LEN (EVP_MD_CTRL_ALG_CTRL+3)
# define EVP_MD_CTRL_SET_KEY (EVP_MD_CTRL_ALG_CTRL+4)
# define EVP_MD_CTRL_MAC_LEN (EVP_MD_CTRL_ALG_CTRL+5)
--- /dev/null
+#include <string.h>
+#include <openssl/cmac.h>
+#include <openssl/conf.h>
+#include <openssl/err.h>
+#include <openssl/evp.h>
+
+#include "e_gost_err.h"
+#include "gost_lcl.h"
+
+typedef struct omac_ctx {
+ CMAC_CTX *cmac_ctx;
+ size_t dgst_size;
+ int cipher_nid;
+ int key_set;
+} OMAC_CTX;
+
+#define MAX_GOST_OMAC_SIZE 16
+
+static int omac_init(EVP_MD_CTX *ctx, int cipher_nid)
+{
+ OMAC_CTX *c = EVP_MD_CTX_md_data(ctx);
+ memset(c, 0, sizeof(OMAC_CTX));
+ c->cipher_nid = cipher_nid;
+ c->key_set = 0;
+
+ switch(cipher_nid) {
+ case NID_magma_cbc:
+ c->dgst_size = 4;
+ break;
+
+ case NID_grasshopper_cbc:
+ c->dgst_size = 8;
+ break;
+ }
+
+ return 1;
+}
+
+static int magma_imit_init(EVP_MD_CTX *ctx)
+{
+ return omac_init(ctx, NID_magma_cbc);
+}
+
+static int grasshopper_imit_init(EVP_MD_CTX *ctx)
+{
+ return omac_init(ctx, NID_grasshopper_cbc);
+}
+
+static int omac_imit_update(EVP_MD_CTX *ctx, const void *data, size_t count)
+{
+ OMAC_CTX *c = EVP_MD_CTX_md_data(ctx);
+ if (!c->key_set)
+ {
+ GOSTerr(GOST_F_OMAC_IMIT_UPDATE, GOST_R_MAC_KEY_NOT_SET);
+ return 0;
+ }
+
+ return CMAC_Update(c->cmac_ctx, data, count);
+}
+
+int omac_imit_final(EVP_MD_CTX *ctx, unsigned char *md)
+{
+ OMAC_CTX *c = EVP_MD_CTX_md_data(ctx);
+ unsigned char mac[MAX_GOST_OMAC_SIZE];
+ size_t mac_size = sizeof(mac);
+
+ if (!c->key_set) {
+ GOSTerr(GOST_F_OMAC_IMIT_FINAL, GOST_R_MAC_KEY_NOT_SET);
+ return 0;
+ }
+
+ CMAC_Final(c->cmac_ctx, mac, &mac_size);
+
+ memcpy(md, mac, c->dgst_size);
+ return 1;
+}
+
+int omac_imit_copy(EVP_MD_CTX *to, const EVP_MD_CTX *from)
+{
+ OMAC_CTX *c_to = EVP_MD_CTX_md_data(to);
+ const OMAC_CTX *c_from = EVP_MD_CTX_md_data(from);
+
+ if (c_from && c_to) {
+ c_to->dgst_size = c_from->dgst_size;
+ c_to->cipher_nid = c_from->cipher_nid;
+ c_to->key_set = c_from->key_set;
+ }
+ else
+ {
+ return 0;
+ }
+ if (c_to->cmac_ctx == c_from->cmac_ctx)
+ {
+ return 1;
+ }
+ return CMAC_CTX_copy(c_to->cmac_ctx, c_from->cmac_ctx);
+}
+
+/* Clean up imit ctx */
+int omac_imit_cleanup(EVP_MD_CTX *ctx)
+{
+ OMAC_CTX *c = EVP_MD_CTX_md_data(ctx);
+
+ if (c)
+ {
+ CMAC_CTX_free(c->cmac_ctx);
+ memset(EVP_MD_CTX_md_data(ctx), 0, sizeof(OMAC_CTX));
+ }
+ return 1;
+}
+
+static int omac_key(OMAC_CTX *c, const EVP_CIPHER *cipher, const unsigned char *key, size_t key_size)
+{
+ int ret = 0;
+
+ c->cmac_ctx = CMAC_CTX_new();
+ if (c->cmac_ctx == NULL)
+ {
+ GOSTerr(GOST_F_OMAC_KEY, ERR_R_MALLOC_FAILURE);
+ return 0;
+ }
+
+ ret = CMAC_Init(c->cmac_ctx, key, key_size, cipher, NULL);
+ if (ret > 0)
+ {
+ c->key_set = 1;
+ }
+ return 1;
+}
+
+int omac_imit_ctrl(EVP_MD_CTX *ctx, int type, int arg, void *ptr)
+{
+ switch (type) {
+ case EVP_MD_CTRL_KEY_LEN:
+ *((unsigned int *)(ptr)) = 32;
+ return 1;
+ case EVP_MD_CTRL_SET_KEY:
+ {
+ OMAC_CTX *c = EVP_MD_CTX_md_data(ctx);
+ const EVP_MD *md = EVP_MD_CTX_md(ctx);
+ const EVP_CIPHER *cipher = NULL;
+
+ if (c->cipher_nid == NID_undef)
+ {
+ switch (EVP_MD_nid(md))
+ {
+ case NID_magma_mac:
+ c->cipher_nid = NID_magma_cbc;
+ break;
+
+ case NID_grasshopper_mac:
+ c->cipher_nid = NID_grasshopper_cbc;
+ break;
+ }
+ }
+ cipher = EVP_get_cipherbynid(c->cipher_nid);
+
+ if (cipher == NULL)
+ {
+ GOSTerr(GOST_F_OMAC_IMIT_CTRL, GOST_R_CIPHER_NOT_FOUND);
+ }
+
+ if (EVP_MD_meth_get_init(EVP_MD_CTX_md(ctx)) (ctx) <= 0) {
+ GOSTerr(GOST_F_OMAC_IMIT_CTRL, GOST_R_MAC_KEY_NOT_SET);
+ return 0;
+ }
+ EVP_MD_CTX_set_flags(ctx, EVP_MD_CTX_FLAG_NO_INIT);
+
+ if (c->key_set)
+ {
+ GOSTerr(GOST_F_OMAC_IMIT_CTRL, GOST_R_BAD_ORDER);
+ return 0;
+ }
+
+ if (arg == 0) {
+ struct gost_mac_key *key = (struct gost_mac_key *)ptr;
+ return omac_key(c, cipher, key->key, 32);
+
+ } else if (arg == 32) {
+ return omac_key(c, cipher, ptr, 32);
+ }
+ GOSTerr(GOST_F_OMAC_IMIT_CTRL, GOST_R_INVALID_MAC_KEY_SIZE);
+ return 0;
+ }
+ case EVP_MD_CTRL_MAC_LEN:
+ {
+ OMAC_CTX *c = EVP_MD_CTX_md_data(ctx);
+ switch (c->cipher_nid)
+ {
+ case NID_magma_cbc:
+ if (arg < 1 || arg > 8) {
+ GOSTerr(GOST_F_OMAC_IMIT_CTRL, GOST_R_INVALID_MAC_SIZE);
+ return 0;
+ }
+ c->dgst_size = arg;
+ break;
+ case NID_grasshopper_cbc:
+ if (arg < 1 || arg > 16) {
+ GOSTerr(GOST_F_OMAC_IMIT_CTRL, GOST_R_INVALID_MAC_SIZE);
+ return 0;
+ }
+ c->dgst_size = arg;
+ break;
+ default:
+ return 0;
+ }
+ return 1;
+ }
+
+ default:
+ return 0;
+ }
+}
+
+static EVP_MD *_hidden_magma_mac_md = NULL;
+
+EVP_MD *magma_omac(void)
+{
+ if (_hidden_magma_mac_md == NULL) {
+ EVP_MD *md;
+
+ if ((md = EVP_MD_meth_new(NID_magma_mac, NID_undef)) == NULL
+ || !EVP_MD_meth_set_result_size(md, 4)
+ || !EVP_MD_meth_set_input_blocksize(md, 8)
+ || !EVP_MD_meth_set_app_datasize(md, sizeof(OMAC_CTX))
+ || !EVP_MD_meth_set_flags(md, 0)
+ || !EVP_MD_meth_set_init(md, magma_imit_init)
+ || !EVP_MD_meth_set_update(md, omac_imit_update)
+ || !EVP_MD_meth_set_final(md, omac_imit_final)
+ || !EVP_MD_meth_set_copy(md, omac_imit_copy)
+ || !EVP_MD_meth_set_cleanup(md, omac_imit_cleanup)
+ || !EVP_MD_meth_set_ctrl(md, omac_imit_ctrl)) {
+ EVP_MD_meth_free(md);
+ md = NULL;
+ }
+ _hidden_magma_mac_md = md;
+ }
+ return _hidden_magma_mac_md;
+}
+
+void magma_omac_destroy(void)
+{
+ EVP_MD_meth_free(_hidden_magma_mac_md);
+ _hidden_magma_mac_md = NULL;
+}
+
+static EVP_MD *_hidden_grasshopper_mac_md = NULL;
+
+EVP_MD *grasshopper_omac(void)
+{
+ if (_hidden_grasshopper_mac_md == NULL) {
+ EVP_MD *md;
+
+ if ((md = EVP_MD_meth_new(NID_grasshopper_mac, NID_undef)) == NULL
+ || !EVP_MD_meth_set_result_size(md, 4)
+ || !EVP_MD_meth_set_input_blocksize(md, 8)
+ || !EVP_MD_meth_set_app_datasize(md, sizeof(OMAC_CTX))
+ || !EVP_MD_meth_set_flags(md, 0)
+ || !EVP_MD_meth_set_init(md, grasshopper_imit_init)
+ || !EVP_MD_meth_set_update(md, omac_imit_update)
+ || !EVP_MD_meth_set_final(md, omac_imit_final)
+ || !EVP_MD_meth_set_copy(md, omac_imit_copy)
+ || !EVP_MD_meth_set_cleanup(md, omac_imit_cleanup)
+ || !EVP_MD_meth_set_ctrl(md, omac_imit_ctrl)) {
+ EVP_MD_meth_free(md);
+ md = NULL;
+ }
+ _hidden_grasshopper_mac_md = md;
+ }
+ return _hidden_grasshopper_mac_md;
+}
+
+void grasshopper_omac_destroy(void)
+{
+ EVP_MD_meth_free(_hidden_grasshopper_mac_md);
+ _hidden_grasshopper_mac_md = NULL;
+}
+
EC_KEY *ec = NULL;
if (!data || data->sign_param_nid == NID_undef) {
- GOSTerr(GOST_F_PKEY_GOST01_PARAMGEN, GOST_R_NO_PARAMETERS_SET);
+ GOSTerr(GOST_F_PKEY_GOST2001_PARAMGEN, GOST_R_NO_PARAMETERS_SET);
return 0;
}
int result = 0;
if (!data || data->sign_param_nid == NID_undef) {
- GOSTerr(GOST_F_PKEY_GOST12_PARAMGEN, GOST_R_NO_PARAMETERS_SET);
+ GOSTerr(GOST_F_PKEY_GOST2012_PARAMGEN, GOST_R_NO_PARAMETERS_SET);
return 0;
}
return 1;
}
+static int pkey_gost_omac_init(EVP_PKEY_CTX *ctx, size_t mac_size)
+{
+ struct gost_mac_pmeth_data *data = OPENSSL_malloc(sizeof(*data));
+ EVP_PKEY *pkey = EVP_PKEY_CTX_get0_pkey(ctx);
+
+ if (!data)
+ return 0;
+ memset(data, 0, sizeof(*data));
+ data->mac_size = mac_size;
+ data->mac_param_nid = NID_undef;
+
+ if (pkey) {
+ struct gost_mac_key *key = EVP_PKEY_get0(pkey);
+ if (key) {
+ data->mac_param_nid = key->mac_param_nid;
+ data->mac_size = key->mac_size;
+ }
+ }
+
+ EVP_PKEY_CTX_set_data(ctx, data);
+ return 1;
+}
+
+static int pkey_gost_magma_mac_init(EVP_PKEY_CTX *ctx)
+{
+ return pkey_gost_omac_init(ctx, 4);
+}
+
+static int pkey_gost_grasshopper_mac_init(EVP_PKEY_CTX *ctx)
+{
+ return pkey_gost_omac_init(ctx, 8);
+}
+
static void pkey_gost_mac_cleanup(EVP_PKEY_CTX *ctx)
{
struct gost_mac_pmeth_data *data = EVP_PKEY_CTX_get_data(ctx);
return -2;
}
+static int pkey_gost_omac_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2, size_t max_size)
+{
+ struct gost_mac_pmeth_data *data =
+ (struct gost_mac_pmeth_data *)EVP_PKEY_CTX_get_data(ctx);
+
+ switch (type) {
+ case EVP_PKEY_CTRL_MD:
+ {
+ int nid = EVP_MD_type((const EVP_MD *)p2);
+ if (nid != NID_magma_mac && nid != NID_grasshopper_mac) {
+ GOSTerr(GOST_F_PKEY_GOST_OMAC_CTRL,
+ GOST_R_INVALID_DIGEST_TYPE);
+ return 0;
+ }
+ data->md = (EVP_MD *)p2;
+ return 1;
+ }
+
+ case EVP_PKEY_CTRL_GET_MD:
+ *(const EVP_MD **)p2 = data->md;
+ return 1;
+
+ case EVP_PKEY_CTRL_PKCS7_ENCRYPT:
+ case EVP_PKEY_CTRL_PKCS7_DECRYPT:
+ case EVP_PKEY_CTRL_PKCS7_SIGN:
+ return 1;
+ case EVP_PKEY_CTRL_SET_MAC_KEY:
+ if (p1 != 32) {
+ GOSTerr(GOST_F_PKEY_GOST_OMAC_CTRL, GOST_R_INVALID_MAC_KEY_LENGTH);
+ return 0;
+ }
+
+ memcpy(data->key, p2, 32);
+ data->key_set = 1;
+ return 1;
+ case EVP_PKEY_CTRL_DIGESTINIT:
+ {
+ EVP_MD_CTX *mctx = p2;
+ struct gost_mac_key *key;
+ if (!data->key_set) {
+ EVP_PKEY *pkey = EVP_PKEY_CTX_get0_pkey(ctx);
+ if (!pkey) {
+ GOSTerr(GOST_F_PKEY_GOST_OMAC_CTRL,
+ GOST_R_MAC_KEY_NOT_SET);
+ return 0;
+ }
+ key = EVP_PKEY_get0(pkey);
+ if (!key) {
+ GOSTerr(GOST_F_PKEY_GOST_OMAC_CTRL,
+ GOST_R_MAC_KEY_NOT_SET);
+ return 0;
+ }
+ return EVP_MD_meth_get_ctrl(EVP_MD_CTX_md(mctx))
+ (mctx, EVP_MD_CTRL_SET_KEY, 0, key);
+ } else {
+ return EVP_MD_meth_get_ctrl(EVP_MD_CTX_md(mctx))
+ (mctx, EVP_MD_CTRL_SET_KEY, 32, &(data->key));
+ }
+ }
+ case EVP_PKEY_CTRL_MAC_LEN:
+ {
+ if (p1 < 1 || p1 > max_size) {
+
+ GOSTerr(GOST_F_PKEY_GOST_OMAC_CTRL, GOST_R_INVALID_MAC_SIZE);
+ return 0;
+ }
+ data->mac_size = p1;
+ return 1;
+ }
+ }
+ return -2;
+}
+
+static int pkey_gost_magma_mac_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2)
+{
+ return pkey_gost_omac_ctrl(ctx, type, p1, p2, 8);
+}
+
+static int pkey_gost_grasshopper_mac_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2)
+{
+ return pkey_gost_omac_ctrl(ctx, type, p1, p2, 16);
+}
+
+static int pkey_gost_omac_ctrl_str(EVP_PKEY_CTX *ctx,
+ const char *type, const char *value, size_t max_size)
+{
+ if (strcmp(type, key_ctrl_string) == 0) {
+ if (strlen(value) != 32) {
+ GOSTerr(GOST_F_PKEY_GOST_OMAC_CTRL_STR,
+ GOST_R_INVALID_MAC_KEY_LENGTH);
+ return 0;
+ }
+ return pkey_gost_mac_ctrl(ctx, EVP_PKEY_CTRL_SET_MAC_KEY,
+ 32, (char *)value);
+ }
+ if (strcmp(type, hexkey_ctrl_string) == 0) {
+ long keylen;
+ int ret;
+ unsigned char *keybuf = string_to_hex(value, &keylen);
+ if (!keybuf || keylen != 32) {
+ GOSTerr(GOST_F_PKEY_GOST_OMAC_CTRL_STR,
+ GOST_R_INVALID_MAC_KEY_LENGTH);
+ OPENSSL_free(keybuf);
+ return 0;
+ }
+ ret = pkey_gost_mac_ctrl(ctx, EVP_PKEY_CTRL_SET_MAC_KEY, 32, keybuf);
+ OPENSSL_free(keybuf);
+ return ret;
+
+ }
+ if (!strcmp(type, maclen_ctrl_string)) {
+ char *endptr;
+ long size = strtol(value, &endptr, 10);
+ if (*endptr != '\0') {
+ GOSTerr(GOST_F_PKEY_GOST_OMAC_CTRL_STR, GOST_R_INVALID_MAC_SIZE);
+ return 0;
+ }
+ return pkey_gost_omac_ctrl(ctx, EVP_PKEY_CTRL_MAC_LEN, size, NULL, max_size);
+ }
+ return -2;
+}
+
+static int pkey_gost_magma_mac_ctrl_str(EVP_PKEY_CTX *ctx,
+ const char *type, const char *value)
+{
+ return pkey_gost_omac_ctrl_str(ctx, type, value, 8);
+}
+
+static int pkey_gost_grasshopper_mac_ctrl_str(EVP_PKEY_CTX *ctx,
+ const char *type, const char *value)
+{
+ return pkey_gost_omac_ctrl_str(ctx, type, value, 8);
+}
+
static int pkey_gost_mac_keygen_base(EVP_PKEY_CTX *ctx,
EVP_PKEY *pkey, int mac_nid)
{
struct gost_mac_pmeth_data *data = EVP_PKEY_CTX_get_data(ctx);
struct gost_mac_key *keydata;
if (!data || !data->key_set) {
- GOSTerr(GOST_F_PKEY_GOST_MAC_KEYGEN, GOST_R_MAC_KEY_NOT_SET);
+ GOSTerr(GOST_F_PKEY_GOST_MAC_KEYGEN_BASE, GOST_R_MAC_KEY_NOT_SET);
return 0;
}
keydata = OPENSSL_malloc(sizeof(struct gost_mac_key));
return pkey_gost_mac_keygen_base(ctx, pkey, NID_id_Gost28147_89_MAC);
}
+static int pkey_gost_magma_mac_keygen(EVP_PKEY_CTX *ctx, EVP_PKEY *pkey)
+{
+ return pkey_gost_mac_keygen_base(ctx, pkey, NID_magma_mac);
+}
+
+static int pkey_gost_grasshopper_mac_keygen(EVP_PKEY_CTX *ctx, EVP_PKEY *pkey)
+{
+ return pkey_gost_mac_keygen_base(ctx, pkey, NID_grasshopper_mac);
+}
+
static int pkey_gost_mac_signctx_init(EVP_PKEY_CTX *ctx, EVP_MD_CTX *mctx)
{
struct gost_mac_pmeth_data *data = EVP_PKEY_CTX_get_data(ctx);
return 1;
}
+static int pkey_gost_magma_mac_signctx_init(EVP_PKEY_CTX *ctx, EVP_MD_CTX *mctx)
+{
+ struct gost_mac_pmeth_data *data = EVP_PKEY_CTX_get_data(ctx);
+
+ if (data == NULL) {
+ pkey_gost_omac_init(ctx, 4);
+ }
+
+ data = EVP_PKEY_CTX_get_data(ctx);
+ if (!data) {
+ GOSTerr(GOST_F_PKEY_GOST_MAGMA_MAC_SIGNCTX_INIT, GOST_R_MAC_KEY_NOT_SET);
+ return 0;
+ }
+
+ return 1;
+}
+
+static int pkey_gost_grasshopper_mac_signctx_init(EVP_PKEY_CTX *ctx, EVP_MD_CTX *mctx)
+{
+ struct gost_mac_pmeth_data *data = EVP_PKEY_CTX_get_data(ctx);
+
+ if (data == NULL) {
+ pkey_gost_omac_init(ctx, 8);
+ }
+
+ data = EVP_PKEY_CTX_get_data(ctx);
+ if (!data) {
+ GOSTerr(GOST_F_PKEY_GOST_GRASSHOPPER_MAC_SIGNCTX_INIT, GOST_R_MAC_KEY_NOT_SET);
+ return 0;
+ }
+
+ return 1;
+}
+
static int pkey_gost_mac_signctx(EVP_PKEY_CTX *ctx, unsigned char *sig,
size_t *siglen, EVP_MD_CTX *mctx)
{
EVP_PKEY_meth_set_cleanup(*pmeth, pkey_gost_mac_cleanup);
EVP_PKEY_meth_set_copy(*pmeth, pkey_gost_mac_copy);
return 1;
+ case NID_magma_mac:
+ EVP_PKEY_meth_set_ctrl(*pmeth, pkey_gost_magma_mac_ctrl,
+ pkey_gost_magma_mac_ctrl_str);
+ EVP_PKEY_meth_set_signctx(*pmeth, pkey_gost_magma_mac_signctx_init,
+ pkey_gost_mac_signctx);
+ EVP_PKEY_meth_set_keygen(*pmeth, NULL, pkey_gost_magma_mac_keygen);
+ EVP_PKEY_meth_set_init(*pmeth, pkey_gost_magma_mac_init);
+ EVP_PKEY_meth_set_cleanup(*pmeth, pkey_gost_mac_cleanup);
+ EVP_PKEY_meth_set_copy(*pmeth, pkey_gost_mac_copy);
+ return 1;
+ case NID_grasshopper_mac:
+ EVP_PKEY_meth_set_ctrl(*pmeth, pkey_gost_grasshopper_mac_ctrl,
+ pkey_gost_grasshopper_mac_ctrl_str);
+ EVP_PKEY_meth_set_signctx(*pmeth, pkey_gost_grasshopper_mac_signctx_init,
+ pkey_gost_mac_signctx);
+ EVP_PKEY_meth_set_keygen(*pmeth, NULL, pkey_gost_grasshopper_mac_keygen);
+ EVP_PKEY_meth_set_init(*pmeth, pkey_gost_grasshopper_mac_init);
+ EVP_PKEY_meth_set_cleanup(*pmeth, pkey_gost_mac_cleanup);
+ EVP_PKEY_meth_set_copy(*pmeth, pkey_gost_mac_copy);
+ return 1;
default: /* Unsupported method */
return 0;
}