Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions src/PublicKey.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,26 @@

namespace TW {

bool validateSignatureLength(TWPublicKeyType type, const Data& signature) {
std::size_t minLength = 64;
std::size_t maxLength = 64;

switch (type) {
case TWPublicKeyTypeSECP256k1:
case TWPublicKeyTypeSECP256k1Extended:
case TWPublicKeyTypeNIST256p1:
case TWPublicKeyTypeNIST256p1Extended: {
maxLength = 65;
break;
}
default: {
break;
}
}

return minLength <= signature.size() && signature.size() <= maxLength;
}

/// Determines if a collection of bytes makes a valid public key of the
/// given type.
bool PublicKey::isValid(const Data& data, enum TWPublicKeyType type) {
Expand Down Expand Up @@ -142,6 +162,10 @@ bool rust_public_key_verify(const Data& key, TWPublicKeyType type, const Data& s
}

bool PublicKey::verify(const Data& signature, const Data& message) const {
if (!validateSignatureLength(type, signature)) {
return false;
}

switch (type) {
case TWPublicKeyTypeSECP256k1:
case TWPublicKeyTypeSECP256k1Extended:
Expand Down
12 changes: 12 additions & 0 deletions tests/interface/TWPublicKeyTests.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,18 @@ TEST(TWPublicKeyTests, Verify) {
ASSERT_TRUE(TWPublicKeyVerify(publicKey.get(), signature.get(), digest.get()));
}

TEST(TWPublicKeyTests, VerifyInvalidLength) {
const PrivateKey key(parse_hex("afeefca74d9a325cf1d6b6911d61a65c32afa8e02bd5e78e2e4ac2910bab45f5"), TWCurveSECP256k1);
const auto privateKey = WRAP(TWPrivateKey, new TWPrivateKey{ key });

const auto message = DATA("de4e9524586d6fce45667f9ff12f661e79870c4105fa0fb58af976619bb11432");
// 63 bytes instead of 64 or 65.
const auto signature = DATA("0000000000000000000000000000000000000000000000000000000000020123456789abcdef0123456789abcdef0123456789abcdef0123456789abcdef80");

auto publicKey = WRAP(TWPublicKey, TWPrivateKeyGetPublicKeySecp256k1(privateKey.get(), false));
ASSERT_FALSE(TWPublicKeyVerify(publicKey.get(), signature.get(), message.get()));
}

TEST(TWPublicKeyTests, VerifyAsDER) {
const PrivateKey key = PrivateKey(parse_hex("afeefca74d9a325cf1d6b6911d61a65c32afa8e02bd5e78e2e4ac2910bab45f5"), TWCurveSECP256k1);
const auto privateKey = WRAP(TWPrivateKey, new TWPrivateKey{ key });
Expand Down
Loading