From: Krzysztof Jackiewicz Date: Mon, 20 Jun 2016 10:50:44 +0000 (+0200) Subject: YACA: Test vector helpers X-Git-Tag: security-manager_5.5_testing~81 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=28aec30f68738d18e9ef5c467a0a19ed1b29c1ff;p=platform%2Fcore%2Ftest%2Fsecurity-tests.git YACA: Test vector helpers Change-Id: I09bb1c03a8ae960f1f788b9a8dca8c1331f5f07f --- diff --git a/CMakeLists.txt b/CMakeLists.txt index c27dd7f6..1c898a36 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -90,6 +90,10 @@ IF(SMACK_ENABLE) ADD_DEFINITIONS("-DWRT_SMACK_ENABLED") ENDIF(SMACK_ENABLE) +IF(NOT DEFINED SHARE_INSTALL_PREFIX) + SET(SHARE_INSTALL_PREFIX "${CMAKE_INSTALL_PREFIX}/share") +ENDIF(NOT DEFINED SHARE_INSTALL_PREFIX) + ############################# Targets names ################################### SET(TARGET_CKM_TESTS "ckm-tests") diff --git a/src/yaca/CMakeLists.txt b/src/yaca/CMakeLists.txt index a712aa3f..f23396c1 100644 --- a/src/yaca/CMakeLists.txt +++ b/src/yaca/CMakeLists.txt @@ -29,6 +29,12 @@ FILE(GLOB yaca_test_SRCS *.cpp) SET(YACA_TEST "yaca-test") ADD_EXECUTABLE(${YACA_TEST} ${yaca_test_SRCS}) +IF(NOT DEFINED YACA_TEST_DIR) + SET(YACA_TEST_DIR "${SHARE_INSTALL_PREFIX}/${YACA_TEST}") +ENDIF(NOT DEFINED YACA_TEST_DIR) +ADD_DEFINITIONS("-DYACA_TEST_DIR=\"${YACA_TEST_DIR}\"") +MESSAGE(STATUS "YACA_TEST_DIR: ${YACA_TEST_DIR}") + ## Link libraries ############################################################## PKG_CHECK_MODULES(YACA_TEST_DEPS REQUIRED yaca) diff --git a/src/yaca/yaca-test-common.cpp b/src/yaca/yaca-test-common.cpp index b779194a..bee1575e 100644 --- a/src/yaca/yaca-test-common.cpp +++ b/src/yaca/yaca-test-common.cpp @@ -56,9 +56,9 @@ const char *yaca_error(int error) return yaca_debug_translate_error(static_cast(error)); } -BufPtr wrap_ptr(char* buffer) +ChrPtr wrap_ptr(char* buffer) { - return BufPtr(buffer, yaca_free); + return ChrPtr(buffer, yaca_free); } KeyPtr wrap_ptr(yaca_key_h key) @@ -71,7 +71,7 @@ CtxPtr wrap_ptr(yaca_context_h ctx) return CtxPtr(ctx, yaca_context_destroy); } -BufPtr create_yaca_buffer(size_t size) +ChrPtr create_yaca_buffer(size_t size) { char *buffer; YACA_SUCCESS(yaca_malloc(size, (void**)&buffer)); @@ -188,11 +188,11 @@ CtxPtr digest_init(yaca_digest_algorithm_e algo) return wrap_ptr(ctx); } -std::vector random_buffer(size_t length) +Buffer random_buffer(size_t length) { RUNNER_ASSERT(length > 0); - std::vector buffer(length); + Buffer buffer(length); std::ifstream is("/dev/urandom", std::ifstream::binary); RUNNER_ASSERT_MSG(is, "Failed to open /dev/urandom"); is.read(buffer.data(), length); diff --git a/src/yaca/yaca-test-common.h b/src/yaca/yaca-test-common.h index 2fc7e3d6..73f5ce2f 100644 --- a/src/yaca/yaca-test-common.h +++ b/src/yaca/yaca-test-common.h @@ -108,15 +108,17 @@ do { \ #define YACA_INVALID_PARAM(func) YACA_RESULT(YACA_ERROR_INVALID_PARAMETER, func); -typedef std::unique_ptr BufPtr; +typedef std::unique_ptr ChrPtr; typedef std::unique_ptr KeyPtr; typedef std::unique_ptr CtxPtr; -BufPtr wrap_ptr(char* buffer); +typedef std::vector Buffer; + +ChrPtr wrap_ptr(char* buffer); KeyPtr wrap_ptr(yaca_key_h key); CtxPtr wrap_ptr(yaca_context_h ctx); -BufPtr create_yaca_buffer(size_t size); +ChrPtr create_yaca_buffer(size_t size); KeyPtr null_key(); @@ -152,14 +154,10 @@ CtxPtr hmac_init(yaca_digest_algorithm_e algo, const KeyPtr& key); CtxPtr digest_init(yaca_digest_algorithm_e algo); -std::vector random_buffer(size_t length); - -/* Converts string representing hex to array of bytes, for example: "d41d" -> { 0xd4, 0x1d } */ -std::vector str2data(const std::string& hex_str); +Buffer random_buffer(size_t length); const char* digest2str(yaca_digest_algorithm_e algo); /* If input is longer than len it is truncated and an ellipsis is appended. * Otherwise the original string is returned. */ std::string truncate_str(const std::string& input, size_t len); - diff --git a/src/yaca/yaca-test-sign.cpp b/src/yaca/yaca-test-sign.cpp index 68b9507a..b65b69db 100644 --- a/src/yaca/yaca-test-sign.cpp +++ b/src/yaca/yaca-test-sign.cpp @@ -83,7 +83,7 @@ RUNNER_TEST(T6030_yaca_sign_final_invalid_param, YacaTest) KeyPtr prv = generate_key(YACA_KEY_TYPE_RSA_PRIV, YACA_KEY_LENGTH_1024BIT); CtxPtr ctx = sign_init(YACA_DIGEST_MD5, prv); size_t sign_len = get_output_length(ctx); - BufPtr sign = create_yaca_buffer(sign_len); + ChrPtr sign = create_yaca_buffer(sign_len); YACA_INVALID_PARAM(yaca_sign_finalize(YACA_CONTEXT_NULL, sign.get(), &sign_len)); YACA_INVALID_PARAM(yaca_sign_finalize(ctx.get(), nullptr, &sign_len)); diff --git a/src/yaca/yaca-test-vector.cpp b/src/yaca/yaca-test-vector.cpp new file mode 100644 index 00000000..c8c3e916 --- /dev/null +++ b/src/yaca/yaca-test-vector.cpp @@ -0,0 +1,178 @@ +/* + * Copyright (c) 2000 - 2016 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License + */ +/* + * @file yaca-test-vector.cpp + * @author Krzysztof Jackiewicz (k.jackiewicz@samsung.com) + * @version 1.0 + */ + +#include + +#include + +#include + +#include "yaca-test-vector.h" + +namespace { + +Buffer hex2bin(const std::string &hex_str) +{ + RUNNER_ASSERT_MSG(hex_str.size() % 2 == 0, + "Length of the provided string is not divisable by 2"); + + /* convert a string representing hex to an array of bytes */ + Buffer data(hex_str.size() / 2); + for (size_t i = 0; i < hex_str.size(); i += 2) { + std::string byte_str = hex_str.substr(i, 2); + std::stringstream ss; + int byte; + + /* Will throw if it can't handle it and that's fine */ + ss << std::hex << byte_str; + ss >> byte; + + RUNNER_ASSERT_MSG(byte == (byte & 0xff), "Byte value out of range"); + + data[i / 2] = static_cast(byte); + } + + return data; +} + +std::map str2digest = { + std::make_pair("MD5", YACA_DIGEST_MD5), + std::make_pair("SHA1", YACA_DIGEST_SHA1), + std::make_pair("SHA224", YACA_DIGEST_SHA224), + std::make_pair("SHA256", YACA_DIGEST_SHA256), + std::make_pair("SHA384", YACA_DIGEST_SHA384), + std::make_pair("SHA512", YACA_DIGEST_SHA512) +}; + +std::map str2encrypt = { + std::make_pair("AES", YACA_ENCRYPT_AES), + std::make_pair("DES", YACA_ENCRYPT_UNSAFE_DES), + std::make_pair("3DES_2TDEA", YACA_ENCRYPT_UNSAFE_3DES_2TDEA), + std::make_pair("3DES_3TDEA", YACA_ENCRYPT_3DES_3TDEA), + std::make_pair("RC2", YACA_ENCRYPT_UNSAFE_RC2), + std::make_pair("RC4", YACA_ENCRYPT_UNSAFE_RC4), + std::make_pair("CAST5", YACA_ENCRYPT_CAST5) +}; + +std::map str2bcm = { + std::make_pair("ECB", YACA_BCM_ECB), + std::make_pair("CTR", YACA_BCM_CTR), + std::make_pair("CBC", YACA_BCM_CBC), + std::make_pair("GCM", YACA_BCM_GCM), + std::make_pair("CFB", YACA_BCM_CFB), + std::make_pair("CFB1", YACA_BCM_CFB1), + std::make_pair("CFB8", YACA_BCM_CFB8), + std::make_pair("OFB", YACA_BCM_OFB), + std::make_pair("CCM", YACA_BCM_CCM) +}; + +} // anonymous namespace + + +void TestVector::add(const std::string &key, const std::string &val) +{ + RUNNER_ASSERT_MSG(m_data.find(key) == m_data.end(), + "The key " << key << " already exists in this test vector"); + m_data[key] = val; +} + +void TestVector::get(const std::string &key, std::string &val) const +{ + val = value(key); +} + +void TestVector::get(const std::string &key, Buffer &val) const +{ + val = hex2bin(value(key)); +} + +void TestVector::get(const std::string &key, yaca_digest_algorithm_e &val) const +{ + val = str2digest.at(value(key)); +} + +void TestVector::get(const std::string &key, yaca_encrypt_algorithm_e &val) const +{ + val = str2encrypt.at(value(key)); +} + +void TestVector::get(const std::string &key, yaca_block_cipher_mode_e &val) const +{ + val = str2bcm.at(value(key)); +} + +void TestVector::reset() +{ + m_data.clear(); +} + +bool TestVector::empty() const +{ + return m_data.empty(); +} + +std::string TestVector::value(const std::string &key) const +{ + auto it = m_data.find(key); + RUNNER_ASSERT_MSG(it != m_data.end(), + "No entry for key \"" << key << "\" in current test vector"); + return it->second; +} + +TestVectorVector loadTestVector(const std::string &filename) +{ + std::string path = std::string(YACA_TEST_DIR"/test-vectors/") + filename; + + TestVectorVector tvv; + + std::ifstream ifs(path, std::ifstream::in); + + RUNNER_ASSERT_MSG(ifs, "Failed to open " << path); + std::string line; + TestVector tv; + while (std::getline(ifs, line)) + { + if (line.empty()) { + /* next test vector */ + if (!tv.empty()) { + tvv.push_back(tv); + tv.reset(); + } + } else { + size_t equals = line.find('='); + + /* ignore lines without '=' */ + if (equals != std::string::npos) + { + std::string key = line.substr(0, equals); + std::string value = line.substr(equals + 1); + tv.add(key, value); + } + } + + if (ifs.eof()) + break; + } + RUNNER_ASSERT_MSG(ifs.eof(), "Failed to read " << path); + if (!tv.empty()) + tvv.push_back(tv); + return tvv; +} diff --git a/src/yaca/yaca-test-vector.h b/src/yaca/yaca-test-vector.h new file mode 100644 index 00000000..d36295ff --- /dev/null +++ b/src/yaca/yaca-test-vector.h @@ -0,0 +1,65 @@ +/* + * Copyright (c) 2000 - 2016 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License + */ +/* + * @file yaca-test-vector.h + * @author Krzysztof Jackiewicz (k.jackiewicz@samsung.com) + * @version 1.0 + */ +#pragma once + +#include +#include +#include +#include + +#include "yaca-test-common.h" + +class TestVector { +public: + TestVector() {} + + void add(const std::string &key, const std::string &value); + + template + void get(const std::string &key, T &val) const + { + std::stringstream ss(value(key)); + ss >> val; + } + /* special case for string (because >> stops on whitespace) */ + void get(const std::string &key, std::string &val) const; + /* special case for buffer */ + void get(const std::string &key, Buffer &val) const; + /* special case for message digest */ + void get(const std::string &key, yaca_digest_algorithm_e &val) const; + /* special case for encryption algorithm */ + void get(const std::string &key, yaca_encrypt_algorithm_e &val) const; + /* special case for bcm */ + void get(const std::string &key, yaca_block_cipher_mode_e &val) const; + + void reset(); + + bool empty() const; +private: + std::string value(const std::string &key) const; + + // key, value + std::map m_data; +}; + +typedef std::vector TestVectorVector; + +TestVectorVector loadTestVector(const std::string &filename);