From bd879d3c9f5fef0107bc3036be3893edab14e89c Mon Sep 17 00:00:00 2001 From: Gabriele Contini <contini.mailing@gmail.com> Date: 周三, 01 1月 2020 20:26:43 +0800 Subject: [PATCH] cleanup & new api --- test/library/LicenseLocator_test.cpp | 13 ++- test/functional/date_test.cpp | 15 +-- src/library/licensecc.cpp | 24 +++-- test/functional/standard-license_test.cpp | 29 +++++- test/library/LicenseReader_test.cpp | 28 ++++--- include/licensecc/datatypes.h | 54 ++++++++---- include/licensecc/licensecc.h | 6 test/functional/volid_test.cpp | 64 ++++++--------- 8 files changed, 133 insertions(+), 100 deletions(-) diff --git a/include/licensecc/datatypes.h b/include/licensecc/datatypes.h index 7a95afb..6f6760c 100644 --- a/include/licensecc/datatypes.h +++ b/include/licensecc/datatypes.h @@ -26,6 +26,8 @@ #define PC_IDENTIFIER_SIZE 19 #define PROPRIETARY_DATA_SIZE 16 #define AUDIT_EVENT_NUM 5 +#define API_LICENSE_DATA_LENGTH 1024 * 4 +#define API_VERSION_LENGTH 16 typedef enum { LICENSE_OK = 0, // OK @@ -62,6 +64,22 @@ char param2[256]; } AuditEvent; +typedef enum { + /** + * A list of absolute path separated by ';' containing the eventual location + * of the license files. Can be NULL. + */ + LICENSE_PATH, + /** + * The license is provided as plain data + */ + LICENSE_PLAIN_DATA, + /** + * The license is encoded + */ + LICENSE_ENCODED +} LICENSE_DATA_TYPE; + /** * This structure contains informations on the raw license data. Software authors * can specify the location of the license file or its full content. @@ -70,25 +88,23 @@ * license file location on its own. */ typedef struct { - /** - * A list of absolute path separated by ';' containing the eventual location - * of the license files. Can be NULL. - */ - const char *licenseFileLocation; - /** - * The application can provide the full license content through this string. - * It can be both in encoded form (base64) or in plain. It's optional. - */ - const char *licenseData; + LICENSE_DATA_TYPE license_data_type; + char licenseData[API_LICENSE_DATA_LENGTH]; } LicenseLocation; + /** * Informations on the software requiring the license */ typedef struct { - char version[16]; // software version in format xxxx.xxxx.xxxx + char version[API_VERSION_LENGTH]; // software version in format xxxx[.xxxx.xxxx] //TODO char project_name[16]; // name of the project (must correspond to the name in the license) - uint32_t magic; // reserved + /** + * this number passed in by the application must correspond to the magic number used when compiling the library. + * See cmake parameter -DLCC_PROJECT_MAGIC_NUM and licensecc_properties.h macro VERIFY_MAGIC + */ + unsigned int magic; } CallerInformations; + typedef struct { /** * Detailed reason of success/failure. Reasons for a failure can be @@ -117,13 +133,13 @@ * in most cases. */ typedef enum { - STRATEGY_DEFAULT, - STRATEGY_ETHERNET, - STRATEGY_IP_ADDRESS, - STRATEGY_DISK_NUM, - STRATEGY_DISK_LABEL, - STRATEGY_PLATFORM_SPECIFIC, - STRATEGY_UNKNOWN + STRATEGY_DEFAULT = -1, + STRATEGY_ETHERNET = 0, + STRATEGY_IP_ADDRESS = 1, + STRATEGY_DISK_NUM = 1, + STRATEGY_DISK_LABEL = 2, + STRATEGY_PLATFORM_SPECIFIC = 3, + STRATEGY_UNKNOWN = -2 } IDENTIFICATION_STRATEGY; #ifdef __cplusplus diff --git a/include/licensecc/licensecc.h b/include/licensecc/licensecc.h index 353eba8..749cf7b 100644 --- a/include/licensecc/licensecc.h +++ b/include/licensecc/licensecc.h @@ -2,8 +2,8 @@ #define LICENSEPP_H_ /* - * This include file is the public api di License++ -*/ + * This include file is the public api di Licensecc + */ #ifdef __cplusplus extern "C" { #endif @@ -20,7 +20,7 @@ * This method calculate the pc identifier. The string has to be shown * to the user in order to calculate the license. */ -bool identify_pc(IDENTIFICATION_STRATEGY pc_id_method, char* identifier_out, size_t bufSize); +bool identify_pc(IDENTIFICATION_STRATEGY pc_id_method, char* identifier_out, size_t* bufSize); /** * This method is used to request the use of one license for a product. diff --git a/src/library/licensecc.cpp b/src/library/licensecc.cpp index ff57cb3..27f3ac7 100644 --- a/src/library/licensecc.cpp +++ b/src/library/licensecc.cpp @@ -25,12 +25,14 @@ using namespace std; void print_error(char out_buffer[256], LicenseInfo* licenseInfo) {} -bool identify_pc(IDENTIFICATION_STRATEGY pc_id_method, char* chbuffer, size_t bufSize) { +bool identify_pc(IDENTIFICATION_STRATEGY pc_id_method, char* chbuffer, size_t* bufSize) { FUNCTION_RETURN result = FUNC_RET_BUFFER_TOO_SMALL; - if (bufSize >= sizeof(PcSignature)) { + if (*bufSize >= sizeof(PcSignature)) { PcSignature identifier_out; result = generate_user_pc_signature(identifier_out, pc_id_method); - strncpy(chbuffer, identifier_out, bufSize); + strncpy(chbuffer, identifier_out, *bufSize); + } else { + *bufSize = sizeof(PcSignature); } return result == FUNC_RET_OK; } @@ -69,16 +71,20 @@ vector<LicenseInfo> licenses_with_errors; vector<LicenseInfo> licenses_ok; license::LicenseVerifier verifier(er); - for (auto it = licenses.begin(); it != licenses.end(); it++) { - FUNCTION_RETURN signatureValid = verifier.verify_signature(*it); + for (auto full_lic_info_it = licenses.begin(); full_lic_info_it != licenses.end(); full_lic_info_it++) { + if (callerInformation != nullptr) { + full_lic_info_it->m_magic = callerInformation->magic; + } + const FUNCTION_RETURN signatureValid = verifier.verify_signature(*full_lic_info_it); + LicenseInfo licInfo = verifier.toLicenseInfo(*full_lic_info_it); if (signatureValid == FUNC_RET_OK) { - if (verifier.verify_limits(*it) == FUNC_RET_OK) { - licenses_ok.push_back(verifier.toLicenseInfo(*it)); + if (verifier.verify_limits(*full_lic_info_it) == FUNC_RET_OK) { + licenses_ok.push_back(licInfo); } else { - licenses_with_errors.push_back(verifier.toLicenseInfo(*it)); + licenses_with_errors.push_back(licInfo); } } else { - licenses_with_errors.push_back(verifier.toLicenseInfo(*it)); + licenses_with_errors.push_back(licInfo); } } if (licenses_ok.size() > 0) { diff --git a/test/functional/date_test.cpp b/test/functional/date_test.cpp index 15fbdd0..83462df 100644 --- a/test/functional/date_test.cpp +++ b/test/functional/date_test.cpp @@ -24,10 +24,10 @@ const string licLocation = generate_license("not_expired.lic", extraArgs); /* */ LicenseInfo license; - LicenseLocation licenseLocation; - licenseLocation.licenseFileLocation = licLocation.c_str(); - licenseLocation.licenseData = ""; - const EVENT_TYPE result = acquire_license(nullptr, &licenseLocation, &license); + LicenseLocation location = {LICENSE_PATH}; + std::copy(licLocation.begin(), licLocation.end(), location.licenseData); + + const EVENT_TYPE result = acquire_license(nullptr, &location, &license); BOOST_CHECK_EQUAL(result, LICENSE_OK); BOOST_CHECK_EQUAL(license.has_expiry, true); BOOST_CHECK_EQUAL(license.linked_to_pc, false); @@ -41,11 +41,10 @@ const string licLocation = generate_license("expired", extraArgs); /* */ LicenseInfo license; - LicenseLocation licenseLocation; - licenseLocation.licenseFileLocation = licLocation.c_str(); - licenseLocation.licenseData = nullptr; + LicenseLocation location = {LICENSE_PATH}; + std::copy(licLocation.begin(), licLocation.end(), location.licenseData); BOOST_TEST_MESSAGE("before acquire license"); - const EVENT_TYPE result = acquire_license(nullptr, &licenseLocation, &license); + const EVENT_TYPE result = acquire_license(nullptr, &location, &license); BOOST_CHECK_EQUAL(result, PRODUCT_EXPIRED); BOOST_CHECK_EQUAL(license.has_expiry, true); BOOST_CHECK_EQUAL(license.linked_to_pc, false); diff --git a/test/functional/standard-license_test.cpp b/test/functional/standard-license_test.cpp index 669ca46..6d55de8 100644 --- a/test/functional/standard-license_test.cpp +++ b/test/functional/standard-license_test.cpp @@ -18,17 +18,34 @@ using namespace std; /** - * Test a generic license with no expiry neither client id. + * Test a generic license with no expiry neither client id. The license is read from file */ -BOOST_AUTO_TEST_CASE(test_generic_license) { +BOOST_AUTO_TEST_CASE(test_generic_license_read_file) { const vector<string> extraArgs; const string licLocation = generate_license("standard_license", extraArgs); /* */ LicenseInfo license; - LicenseLocation licenseLocation; - licenseLocation.licenseFileLocation = licLocation.c_str(); - licenseLocation.licenseData = nullptr; - const EVENT_TYPE result = acquire_license(nullptr, &licenseLocation, &license); + LicenseLocation location = {LICENSE_PATH}; + std::copy(licLocation.begin(), licLocation.end(), location.licenseData); + const EVENT_TYPE result = acquire_license(nullptr, &location, &license); + BOOST_CHECK_EQUAL(result, LICENSE_OK); + BOOST_CHECK_EQUAL(license.has_expiry, false); + BOOST_CHECK_EQUAL(license.linked_to_pc, false); +} + +/** + * Test a generic license with no expiry neither client id. The license is passed in trhough the licenseData structure. + */ +BOOST_AUTO_TEST_CASE(test_read_license_data) { + const vector<string> extraArgs; + const fs::path licLocation = fs::path(generate_license("standard_license1", extraArgs)); + string license_data; + // load the license string + fs::load_string_file(licLocation, license_data); + LicenseInfo license; + LicenseLocation location = {LICENSE_PLAIN_DATA}; + std::copy(license_data.begin(), license_data.end(), location.licenseData); + const EVENT_TYPE result = acquire_license(nullptr, &location, &license); BOOST_CHECK_EQUAL(result, LICENSE_OK); BOOST_CHECK_EQUAL(license.has_expiry, false); BOOST_CHECK_EQUAL(license.linked_to_pc, false); diff --git a/test/functional/volid_test.cpp b/test/functional/volid_test.cpp index 53dfae3..b6a808a 100644 --- a/test/functional/volid_test.cpp +++ b/test/functional/volid_test.cpp @@ -22,13 +22,12 @@ namespace license { namespace test { -BOOST_AUTO_TEST_CASE( default_volid_lic_file ) { +BOOST_AUTO_TEST_CASE(default_volid_lic_file) { PcSignature identifier_out; const IDENTIFICATION_STRATEGY strategy = IDENTIFICATION_STRATEGY::STRATEGY_ETHERNET; BOOST_TEST_CHECKPOINT("Before generate"); - const FUNCTION_RETURN generate_ok = generate_user_pc_signature(identifier_out, - strategy); + const FUNCTION_RETURN generate_ok = generate_user_pc_signature(identifier_out, strategy); BOOST_TEST_CHECKPOINT("After generate signature"); BOOST_ASSERT(generate_ok == FUNCTION_RETURN::FUNC_RET_OK); cout << "Identifier:" << identifier_out << endl; @@ -39,25 +38,22 @@ const string licLocation = generate_license("volid_license", extraArgs); LicenseInfo license; - LicenseLocation licenseLocation; - licenseLocation.licenseFileLocation = licLocation.c_str(); - licenseLocation.licenseData = ""; - const EVENT_TYPE result = acquire_license(nullptr, &licenseLocation, &license); + LicenseLocation location = {LICENSE_PATH}; + std::copy(licLocation.begin(), licLocation.end(), location.licenseData); + const EVENT_TYPE result = acquire_license(nullptr, &location, &license); BOOST_CHECK_EQUAL(result, LICENSE_OK); BOOST_CHECK_EQUAL(license.has_expiry, false); BOOST_CHECK_EQUAL(license.linked_to_pc, true); } -static void generate_reference_file(const string &idfileLocation, - IDENTIFICATION_STRATEGY strategies[], int num_strategies) { +static void generate_reference_file(const string &idfileLocation, IDENTIFICATION_STRATEGY strategies[], + int num_strategies) { ofstream idfile(idfileLocation); PcSignature identifier_out; for (int i = 0; i < num_strategies; i++) { - FUNCTION_RETURN generate_ok = generate_user_pc_signature(identifier_out, - strategies[i]); + FUNCTION_RETURN generate_ok = generate_user_pc_signature(identifier_out, strategies[i]); if (generate_ok != FUNC_RET_OK) { - BOOST_ERROR( - "Generating identifier for strategy " << strategies[i] << " failed with: " << generate_ok); + BOOST_ERROR("Generating identifier for strategy " << strategies[i] << " failed with: " << generate_ok); idfile << "0000-0000-0000-0000" << endl; BOOST_ASSERT(generate_ok == FUNC_RET_OK); } else @@ -71,69 +67,61 @@ std::vector<IDENTIFICATION_STRATEGY> strategies; size_t disk_num; getDiskInfos(NULL, &disk_num); - if (disk_num >0) { + if (disk_num > 0) { strategies = {STRATEGY_DEFAULT, STRATEGY_DISK_NUM, STRATEGY_DISK_LABEL}; } else { BOOST_TEST_CHECKPOINT("if no disk default strategy fails see #49"); - //strategies = { DEFAULT }; + // strategies = { DEFAULT }; strategies = {}; } size_t adapters; getAdapterInfos(nullptr, &adapters); - if(adapters > 0){ + if (adapters > 0) { strategies.push_back(STRATEGY_ETHERNET); } size_t num_strategies = strategies.size(); - if(num_strategies == 0) { - //see issue #49 can't use default + if (num_strategies == 0) { + // see issue #49 can't use default return; } std::ifstream test_idfile_exist(idfileLocation); if (!test_idfile_exist.good()) { - generate_reference_file(idfileLocation, strategies.data(), - strategies.size()); + generate_reference_file(idfileLocation, strategies.data(), strategies.size()); } else { std::istream_iterator<string> start(test_idfile_exist), end; std::vector<string> reference_signatures(start, end); test_idfile_exist.close(); - if (reference_signatures.size() != num_strategies - || std::find(reference_signatures.begin(), - reference_signatures.end(), "0000-0000-0000-0000") - != reference_signatures.end()) + if (reference_signatures.size() != num_strategies || + std::find(reference_signatures.begin(), reference_signatures.end(), "0000-0000-0000-0000") != + reference_signatures.end()) generate_reference_file(idfileLocation, strategies.data(), num_strategies); } std::ifstream is(idfileLocation); std::istream_iterator<string> start(is), end; std::vector<string> reference_signatures(start, end); - BOOST_TEST_CHECKPOINT( - "Generating current signatures and comparing with past"); + BOOST_TEST_CHECKPOINT("Generating current signatures and comparing with past"); for (int i = 0; i < num_strategies; i++) { PcSignature generated_identifier; - FUNCTION_RETURN generate_ok = generate_user_pc_signature( - generated_identifier, strategies[i]); + FUNCTION_RETURN generate_ok = generate_user_pc_signature(generated_identifier, strategies[i]); BOOST_ASSERT(generate_ok == FUNCTION_RETURN::FUNC_RET_OK); if (generate_ok != FUNC_RET_OK) { - BOOST_ERROR( - "Generating identifier for strategy " << strategies[i] << " failed with: " << generate_ok); + BOOST_ERROR("Generating identifier for strategy " << strategies[i] << " failed with: " << generate_ok); continue; } if (reference_signatures[i] != generated_identifier) { - string message = string("pc signature compare fail: strategy: ") - + to_string(static_cast<long long>(strategies[i])) - + " generated: [" + generated_identifier + "] reference: [" - + reference_signatures[i] + "]"; + string message = string("pc signature compare fail: strategy: ") + + to_string(static_cast<long long>(strategies[i])) + " generated: [" + generated_identifier + + "] reference: [" + reference_signatures[i] + "]"; BOOST_ERROR(message); } } BOOST_TEST_CHECKPOINT("Verifying signatures"); for (int j = 0; j < 100; j++) { for (unsigned int i = 0; i < reference_signatures.size(); i++) { - if (reference_signatures[i] == "0000-0000-0000-0000") - continue; + if (reference_signatures[i] == "0000-0000-0000-0000") continue; PcSignature pcsig; - strncpy(pcsig, reference_signatures[i].c_str(), - sizeof(PcSignature) - 1); + strncpy(pcsig, reference_signatures[i].c_str(), sizeof(PcSignature) - 1); EVENT_TYPE val_result = validate_pc_signature(pcsig); BOOST_TEST_CHECKPOINT("Verifying signature: "); BOOST_CHECK_EQUAL(val_result, LICENSE_OK); diff --git a/test/library/LicenseLocator_test.cpp b/test/library/LicenseLocator_test.cpp index 6c83fc0..65c225a 100644 --- a/test/library/LicenseLocator_test.cpp +++ b/test/library/LicenseLocator_test.cpp @@ -1,10 +1,11 @@ #define BOOST_TEST_MODULE "test_license_locator" +#define __STDC_WANT_LIB_EXT1__ 1 +#include <string.h> #include <iostream> #include <iterator> #include <cstdio> #include <fstream> -#include <string> #include <vector> #include <boost/filesystem.hpp> #include <boost/optional.hpp> @@ -88,13 +89,14 @@ BOOST_AUTO_TEST_CASE(external_definition) { // an application can define multiple license locations separated by ';' - const char *applicationDefinedString = MOCK_LICENSE ";/this/one/doesnt/exist"; + string applicationDefinedString = MOCK_LICENSE ";/this/one/doesnt/exist"; // read test license std::ifstream src(MOCK_LICENSE, std::ios::binary); std::string referenceContent((std::istreambuf_iterator<char>(src)), std::istreambuf_iterator<char>()); license::EventRegistry registry; - const LicenseLocation licLocation = {applicationDefinedString, nullptr}; + LicenseLocation licLocation = {LICENSE_PATH}; + std::copy(applicationDefinedString.begin(), applicationDefinedString.end(), licLocation.licenseData); ExternalDefinition externalDefinition(&licLocation); vector<string> licenseInfos = externalDefinition.license_locations(registry); BOOST_CHECK(registry.isGood()); @@ -109,9 +111,10 @@ * The license file doesn't exist. Check that the locator reports the right error */ BOOST_AUTO_TEST_CASE(external_definition_not_found) { - const char *applicationDefinedString = PROJECT_TEST_SRC_DIR "/this/file/doesnt/exist"; + string applicationDefinedString = PROJECT_TEST_SRC_DIR "/this/file/doesnt/exist"; license::EventRegistry registry; - const LicenseLocation licLocation = {applicationDefinedString, nullptr}; + LicenseLocation licLocation = {LICENSE_PATH}; + std::copy(applicationDefinedString.begin(), applicationDefinedString.end(), licLocation.licenseData); ExternalDefinition externalDefinition(&licLocation); vector<string> licenseInfos = externalDefinition.license_locations(registry); diff --git a/test/library/LicenseReader_test.cpp b/test/library/LicenseReader_test.cpp index 0b16149..57ed1dc 100644 --- a/test/library/LicenseReader_test.cpp +++ b/test/library/LicenseReader_test.cpp @@ -1,4 +1,7 @@ #define BOOST_TEST_MODULE "test_license_reader" +#define __STDC_WANT_LIB_EXT1__ 1 + +#include <string> #include <boost/test/unit_test.hpp> #include <iostream> @@ -22,10 +25,11 @@ * Read license at application provided location */ BOOST_AUTO_TEST_CASE(read_single_file) { - const char *licLocation = PROJECT_TEST_SRC_DIR "/library/test_reader.ini"; + string location = PROJECT_TEST_SRC_DIR "/library/test_reader.ini"; - const LicenseLocation location = {licLocation, nullptr}; - LicenseReader licenseReader(&location); + LicenseLocation licLocation = {LICENSE_PATH}; + std::copy(location.begin(), location.end(), licLocation.licenseData); + LicenseReader licenseReader(&licLocation); vector<FullLicenseInfo> licenseInfos; const EventRegistry registry = licenseReader.readLicenses("PrODUCT", licenseInfos); BOOST_CHECK(registry.isGood()); @@ -36,9 +40,10 @@ * Test the error return if the product code is not found in the license */ BOOST_AUTO_TEST_CASE(product_not_licensed) { - const char *licLocation = PROJECT_TEST_SRC_DIR "/library/test_reader.ini"; - const LicenseLocation location = {licLocation, nullptr}; - LicenseReader licenseReader(&location); + string location = PROJECT_TEST_SRC_DIR "/library/test_reader.ini"; + LicenseLocation licLocation = {LICENSE_PATH}; + std::copy(location.begin(), location.end(), licLocation.licenseData); + LicenseReader licenseReader(&licLocation); vector<FullLicenseInfo> licenseInfos; const EventRegistry registry = licenseReader.readLicenses("PRODUCT-NOT", licenseInfos); BOOST_CHECK(!registry.isGood()); @@ -51,11 +56,12 @@ * Test the error code if the license file is specified but doesn't exists */ BOOST_AUTO_TEST_CASE(file_not_found) { - const char *licLocation = PROJECT_TEST_SRC_DIR "/library/not_found.ini"; + string licLocation = PROJECT_TEST_SRC_DIR "/library/not_found.ini"; locate::LocatorFactory::find_license_near_module(false); locate::LocatorFactory::find_license_with_env_var(false); - const LicenseLocation location = {licLocation, nullptr}; + LicenseLocation location = {LICENSE_PATH}; + std::copy(licLocation.begin(), licLocation.end(), location.licenseData); LicenseReader licenseReader(&location); vector<FullLicenseInfo> licenseInfos; const EventRegistry registry = licenseReader.readLicenses("PRODUCT", licenseInfos); @@ -70,10 +76,9 @@ */ BOOST_AUTO_TEST_CASE(env_var_not_defined) { UNSETENV(LICENSE_LOCATION_ENV_VAR); - const LicenseLocation location = {nullptr, nullptr}; locate::LocatorFactory::find_license_near_module(false); locate::LocatorFactory::find_license_with_env_var(true); - LicenseReader licenseReader(&location); + LicenseReader licenseReader(nullptr); vector<FullLicenseInfo> licenseInfos; const EventRegistry registry = licenseReader.readLicenses("PRODUCT", licenseInfos); BOOST_CHECK(!registry.isGood()); @@ -93,8 +98,7 @@ locate::LocatorFactory::find_license_near_module(false); locate::LocatorFactory::find_license_with_env_var(true); - const LicenseLocation location = {nullptr, nullptr}; - LicenseReader licenseReader(&location); + LicenseReader licenseReader(nullptr); vector<FullLicenseInfo> licenseInfos; const EventRegistry registry = licenseReader.readLicenses("PRODUCT", licenseInfos); cout << registry << endl; -- Gitblit v1.9.1