Skip to content

Commit

Permalink
bugfix in bcrypt has and key swap; performance measurement helpers
Browse files Browse the repository at this point in the history
  • Loading branch information
vladp72 committed Oct 25, 2019
1 parent 9d583cb commit cd36c9a
Show file tree
Hide file tree
Showing 5 changed files with 565 additions and 25 deletions.
34 changes: 10 additions & 24 deletions include/hbcrypt.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -1171,11 +1171,11 @@ namespace bcrypt {

void swap(hash &other) noexcept {
BCRYPT_HASH_HANDLE h{h_};
hcrypt::buffer b{b_};
hcrypt::buffer b{std::move(b_)};
h_ = other.h_;
b_ = other.b_;
b_ = std::move(other.b_);
other.h_ = h;
other.b_ = b;
other.b_ = std::move(b);
}

bool is_valid() const noexcept {
Expand All @@ -1189,15 +1189,8 @@ namespace bcrypt {
[[nodiscard]] std::error_code try_duplicate_to(hash *hash) const noexcept {
std::error_code status{hcrypt::win32_error(ERROR_SUCCESS)};
if (hash != this) {
unsigned long hash_size{0};
status = try_get_object_length(&hash_size);

if (hcrypt::is_failure(status)) {
return status;
}

hcrypt::buffer b;
status = hcrypt::try_resize(b, hash_size);
status = hcrypt::try_resize(b, b_.size());

if (hcrypt::is_failure(status)) {
return status;
Expand Down Expand Up @@ -1227,7 +1220,7 @@ namespace bcrypt {
hash hash_duplicate;

hcrypt::buffer b;
b.resize(get_object_length());
b.resize(b_.size());

BCRYPT_HASH_HANDLE h{nullptr};

Expand Down Expand Up @@ -1554,11 +1547,11 @@ namespace bcrypt {

void swap(key &other) noexcept {
BCRYPT_KEY_HANDLE h{h_};
hcrypt::buffer b{b_};
hcrypt::buffer b{std::move(b_)};
h_ = other.h_;
b_ = other.b_;
b_ = std::move(other.b_);
other.h_ = h;
other.b_ = b;
other.b_ = std::move(b);
}

bool is_valid() const noexcept {
Expand All @@ -1573,15 +1566,8 @@ namespace bcrypt {
std::error_code status{hcrypt::win32_error(ERROR_SUCCESS)};

if (key != this) {
unsigned long key_size{0};
status = try_get_key_object_length(&key_size);

if (hcrypt::is_failure(status)) {
return status;
}

hcrypt::buffer b;
status = hcrypt::try_resize(b, key_size);
status = hcrypt::try_resize(b, b_.size());
if (hcrypt::is_failure(status)) {
return status;
}
Expand Down Expand Up @@ -1611,7 +1597,7 @@ namespace bcrypt {
key key_duplicate;

hcrypt::buffer b;
b.resize(get_key_object_length());
b.resize(b_.size());

BCRYPT_KEY_HANDLE h{nullptr};

Expand Down
75 changes: 75 additions & 0 deletions test/hbcrypt_test_hash.cpp
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
#include "hbcrypt_test_hash.hpp"
#include <algorithm>
#include "perf\hcrypt_perf.hpp"

namespace {

Expand Down Expand Up @@ -40,6 +41,20 @@ namespace {
ex.what());
}
}

void perf_sample_hash_create(wchar_t const *algorithm_name,
hcrypt::buffer const &data_to_hash) {
bcrypt::algorithm_provider provider{algorithm_name};
bcrypt::hash h{provider.create_hash()};
h.hash_data(data_to_hash.data(), data_to_hash.size());
hcrypt::buffer hash_value{h.finish()};
}

void perf_sample_hash_duplicate(bcrypt::hash &hash, hcrypt::buffer const &data_to_hash) {
bcrypt::hash h{hash};
h.hash_data(data_to_hash.data(), data_to_hash.size());
hcrypt::buffer hash_value{h.finish()};
}
} // namespace

void test_sample_hash() {
Expand Down Expand Up @@ -67,3 +82,63 @@ void test_sample_hash() {
}
printf("\n----------------\n");
}

void perf_sample_hash() {
try {
int offset{0};

hcrypt::buffer data_to_hash;
data_to_hash.resize(4 * 1024);
bcrypt::generate_random(data_to_hash.data(), data_to_hash.size());

//
// Use it to warm up
//
printf("\n%*cWarming up.\n", offset + 2, ' ');
perf::samples_collection warm_up_samples;
warm_up_samples.measure([&data_to_hash]() {
perf_sample_hash_create(BCRYPT_MD2_ALGORITHM, data_to_hash);
});

std::for_each(
std::begin(hash_algorithms),
std::end(hash_algorithms),
[offset, &data_to_hash](wchar_t const *algorithm_name) {
printf("\n%*cMeasuring perf for %S creating hash.\n", offset + 2, ' ', algorithm_name);
try {
perf::samples_collection samples;
samples.measure([&data_to_hash, algorithm_name]() {
perf_sample_hash_create(algorithm_name, data_to_hash);
});
perf::result_t result{samples.calculate_result()};
result.print(offset + 2);
} catch (std::system_error const &ex) {
printf("aborted, error code = 0x%x, %s\n", ex.code().value(), ex.what());
}

printf("\n%*cMeasuring perf for %S duplicating hash.\n", offset + 2, ' ', algorithm_name);
try {
bcrypt::algorithm_provider provider{algorithm_name};
bcrypt::hash h{provider.create_hash()};

perf::samples_collection samples;

samples.measure([&data_to_hash, &h]() {
perf_sample_hash_duplicate(h, data_to_hash);
});
perf::result_t result{samples.calculate_result()};
result.print(offset + 2);
} catch (std::system_error const &ex) {
printf(
"aborted, error code = 0x%x, %s\n",
ex.code().value(),
ex.what());
}

});

} catch (std::system_error const &ex) {
printf("perf_sample_hash, error code = 0x%x, %s\n", ex.code().value(), ex.what());
}
printf("\n----------------\n");
}
3 changes: 2 additions & 1 deletion test/hbcrypt_test_hash.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,5 @@

#include "hcrypt_test_helpers.hpp"

void test_sample_hash();
void test_sample_hash();
void perf_sample_hash();
2 changes: 2 additions & 0 deletions test/hcrypt_test.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,8 @@ int main() {

test_sample_ncrypt_key_derivation();

perf_sample_hash();

//
// This test prompts user to enter password that
// protects key. Run it only in interactive mode
Expand Down
Loading

0 comments on commit cd36c9a

Please sign in to comment.