secp256k1zkp 0.9.2 → 0.9.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/ext/secp256k1zkp/secp256k1zkp.c +11 -5
- data/lib/secp256k1zkp.rb +1 -1
- data/lib/secp256k1zkp/private_key.rb +39 -17
- data/lib/secp256k1zkp/public_key.rb +27 -5
- data/lib/secp256k1zkp/utility.rb +60 -0
- data/lib/secp256k1zkp/version.rb +1 -1
- metadata +17 -3
- data/lib/secp256k1zkp/utils.rb +0 -20
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6f9f439836bf01ac6f1b0ac87ffe86d574fb0940
|
4
|
+
data.tar.gz: e4aa8985dd05aa5be9cb5defa141876ad21aaf10
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: becdcd95251016ab442147136c8ceb95d98a66395a96357e4311acb28428f8e85df084b28c18ea4bb8c88bc234b1adead3963b3ac7fba964744a8876b183f58f
|
7
|
+
data.tar.gz: f1cf4ed558e7017f36427b1571918ae788c94a7885d2526c2f46b1ccc0bb7237f688449b318e53761f541347eb7649246134232869b3564a13ba547fb04bd5ff
|
@@ -265,7 +265,7 @@ static int is_canonical(const rb_struct_compact_signature *sign)
|
|
265
265
|
}
|
266
266
|
|
267
267
|
/**
|
268
|
-
* Secp256k1Zkp::Context#sign_compact(message_digest, private_key)
|
268
|
+
* Secp256k1Zkp::Context#sign_compact(message_digest, private_key[, require_canonical = true])
|
269
269
|
*
|
270
270
|
* 生成紧凑格式的 ECDSA 签名(recId + 64字节)。
|
271
271
|
*
|
@@ -273,8 +273,9 @@ static int is_canonical(const rb_struct_compact_signature *sign)
|
|
273
273
|
* @param private_key [Secp256k1Zkp::PrivateKey] 私钥。
|
274
274
|
* @return [String]
|
275
275
|
*/
|
276
|
-
static VALUE dm_context_sign_compact(
|
276
|
+
static VALUE dm_context_sign_compact(int argc, VALUE *argv, VALUE self)
|
277
277
|
{
|
278
|
+
VALUE message_digest, private_key, v_require_canonical;
|
278
279
|
rb_struct_context *context;
|
279
280
|
rb_struct_private_key *sp_private_key;
|
280
281
|
const unsigned char *digest32;
|
@@ -285,6 +286,11 @@ static VALUE dm_context_sign_compact(VALUE self, VALUE message_digest, VALUE pri
|
|
285
286
|
0,
|
286
287
|
};
|
287
288
|
|
289
|
+
if (2 == rb_scan_args(argc, argv, "21", &message_digest, &private_key, &v_require_canonical))
|
290
|
+
{
|
291
|
+
v_require_canonical = Qtrue;
|
292
|
+
}
|
293
|
+
|
288
294
|
SafeStringValue(message_digest);
|
289
295
|
if (RSTRING_LEN(message_digest) != kByteSizeSha256)
|
290
296
|
{
|
@@ -304,9 +310,9 @@ static VALUE dm_context_sign_compact(VALUE self, VALUE message_digest, VALUE pri
|
|
304
310
|
|
305
311
|
// 初始化部分参数
|
306
312
|
digest32 = (const unsigned char *)RSTRING_PTR(message_digest);
|
307
|
-
require_canonical =
|
313
|
+
require_canonical = RTEST(v_require_canonical) ? 1 : 0;
|
308
314
|
counter = 0;
|
309
|
-
|
315
|
+
|
310
316
|
// 循环计算签名,直到找到合适的 canonical 签名。
|
311
317
|
do
|
312
318
|
{
|
@@ -708,7 +714,7 @@ void Init_secp256k1zkp()
|
|
708
714
|
rb_define_method(rb_cSecp256k1Context, "is_valid_private_keydata?", dm_context_verify_private_keydata, 1);
|
709
715
|
rb_define_method(rb_cSecp256k1Context, "clone", dm_context_clone, 0);
|
710
716
|
rb_define_method(rb_cSecp256k1Context, "dup", dm_context_clone, 0);
|
711
|
-
rb_define_method(rb_cSecp256k1Context, "sign_compact", dm_context_sign_compact,
|
717
|
+
rb_define_method(rb_cSecp256k1Context, "sign_compact", dm_context_sign_compact, -1);
|
712
718
|
rb_define_method(rb_cSecp256k1Context, "pedersen_commit", dm_context_pedersen_commit, 2);
|
713
719
|
rb_define_method(rb_cSecp256k1Context, "pedersen_blind_sum", dm_context_pedersen_blind_sum, 2);
|
714
720
|
rb_define_method(rb_cSecp256k1Context, "range_proof_sign", dm_context_range_proof_sign, 7);
|
data/lib/secp256k1zkp.rb
CHANGED
@@ -2,29 +2,51 @@
|
|
2
2
|
|
3
3
|
require 'securerandom'
|
4
4
|
|
5
|
-
|
5
|
+
class Secp256k1Zkp::PrivateKey
|
6
6
|
|
7
|
-
|
7
|
+
include Secp256k1Zkp::Utility
|
8
8
|
|
9
|
-
|
10
|
-
# # => REMARK:私钥有效范围。[1, secp256k1 curve order)。REMARK:大部分 lib 范围是 [1, secp256k1 curve order] 的闭区间,c库范围为开区间。
|
11
|
-
# sec = SecureRandom.random_number(0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141 - 1) + 1
|
12
|
-
# new(hex_decode("%064x" % sec))
|
13
|
-
new(SecureRandom.random_bytes(32))
|
14
|
-
end
|
9
|
+
SECP256K1_CURVE_ORDER = 0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFEBAAEDCE6AF48A03BBFD25E8CD0364141
|
15
10
|
|
16
|
-
|
17
|
-
|
18
|
-
|
11
|
+
def self.nonce
|
12
|
+
# => 私钥有效范围。[1, SECP256K1_CURVE_ORDER)。 REMARK:大部分 lib 范围是 [1, SECP256K1_CURVE_ORDER] 的闭区间,该C库范围为开区间。
|
13
|
+
SecureRandom.random_number(SECP256K1_CURVE_ORDER - 1) + 1
|
14
|
+
end
|
19
15
|
|
20
|
-
|
21
|
-
|
22
|
-
|
16
|
+
def self.random
|
17
|
+
new(hex_decode("%064x" % self.nonce))
|
18
|
+
end
|
23
19
|
|
24
|
-
|
25
|
-
|
26
|
-
|
20
|
+
# => role - owner / active
|
21
|
+
def self.from_account_and_password(account, password, role = 'active')
|
22
|
+
return from_seed(format("%s%s%s", account, role, password))
|
23
|
+
end
|
24
|
+
|
25
|
+
def self.from_seed(seed)
|
26
|
+
return new(sha256(seed))
|
27
|
+
end
|
28
|
+
|
29
|
+
def self.from_wif(wif_private_key_string)
|
30
|
+
raw = base58_decode(wif_private_key_string)
|
31
|
+
version = raw[0].unpack("C").first
|
32
|
+
raise 'invalid private key.' if version != 0x80
|
33
|
+
# => raw = [1B]0x80 + [32B]privatekey + [4B]checksum
|
34
|
+
checksum_size = 4
|
35
|
+
checksum4 = raw[-checksum_size..-1]
|
36
|
+
private_key_with_prefix = raw[0...-checksum_size]
|
37
|
+
digest = sha256(sha256(private_key_with_prefix))
|
38
|
+
raise 'invalid private key.' if checksum4 != digest[0, checksum_size]
|
39
|
+
return new(raw[1, 32])
|
40
|
+
end
|
41
|
+
|
42
|
+
def to_wif
|
43
|
+
private_key_with_prefix = 0x80.chr + self.bytes
|
44
|
+
checksum = sha256(sha256(private_key_with_prefix))[0, 4]
|
45
|
+
return base58_encode(private_key_with_prefix + checksum)
|
46
|
+
end
|
27
47
|
|
48
|
+
def shared_secret(public_key)
|
49
|
+
return public_key * self.bytes
|
28
50
|
end
|
29
51
|
|
30
52
|
end
|
@@ -1,13 +1,35 @@
|
|
1
1
|
#encoding:utf-8
|
2
2
|
|
3
|
-
|
3
|
+
class Secp256k1Zkp::PublicKey
|
4
4
|
|
5
|
-
|
5
|
+
include Secp256k1Zkp::Utility
|
6
6
|
|
7
|
-
|
8
|
-
|
9
|
-
|
7
|
+
def self.from_wif(wif_public_key, public_key_prefix = 'BTS')
|
8
|
+
prefix_size = public_key_prefix.bytesize
|
9
|
+
prefix = wif_public_key[0, prefix_size]
|
10
|
+
raise 'invalid public key prefix.' if prefix != public_key_prefix
|
10
11
|
|
12
|
+
raw = base58_decode(wif_public_key[prefix_size..-1])
|
13
|
+
checksum_size = 4
|
14
|
+
compression_public_key = raw[0, raw.bytesize - checksum_size]
|
15
|
+
checksum4 = raw[-checksum_size..-1]
|
16
|
+
raise 'invalid public key.' if checksum4 != rmd160(compression_public_key)[0, checksum_size]
|
17
|
+
return new(compression_public_key)
|
18
|
+
end
|
19
|
+
|
20
|
+
def to_wif(public_key_prefix = 'BTS')
|
21
|
+
checksum = rmd160(self.bytes)
|
22
|
+
addr = self.bytes + checksum[0, 4]
|
23
|
+
return public_key_prefix + base58_encode(addr)
|
24
|
+
end
|
25
|
+
|
26
|
+
# => (public) 生成bts地址(序列化时公钥排序会用到。)
|
27
|
+
def to_blockchain_address
|
28
|
+
return rmd160(sha512(self.bytes))
|
29
|
+
end
|
30
|
+
|
31
|
+
def shared_secret(private_key)
|
32
|
+
return self * private_key.bytes
|
11
33
|
end
|
12
34
|
|
13
35
|
end
|
@@ -0,0 +1,60 @@
|
|
1
|
+
#encoding:utf-8
|
2
|
+
|
3
|
+
require 'digest'
|
4
|
+
require 'base58'
|
5
|
+
|
6
|
+
module Secp256k1Zkp
|
7
|
+
|
8
|
+
module Utility
|
9
|
+
|
10
|
+
def md5(data, raw = true)
|
11
|
+
if raw
|
12
|
+
return Digest::MD5.digest(data)
|
13
|
+
else
|
14
|
+
return Digest::MD5.hexdigest(data)
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
def sha256(data, raw = true)
|
19
|
+
if raw
|
20
|
+
return Digest::SHA256.digest(data)
|
21
|
+
else
|
22
|
+
return Digest::SHA256.hexdigest(data)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
def sha512(data, raw = true)
|
27
|
+
if raw
|
28
|
+
return Digest::SHA512.digest(data)
|
29
|
+
else
|
30
|
+
return Digest::SHA512.hexdigest(data)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def rmd160(data, raw = true)
|
35
|
+
if raw
|
36
|
+
return Digest::RMD160.digest(data)
|
37
|
+
else
|
38
|
+
return Digest::RMD160.hexdigest(data)
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
def hex_encode(data)
|
43
|
+
return data.unpack("H*").first.downcase
|
44
|
+
end
|
45
|
+
|
46
|
+
def hex_decode(data)
|
47
|
+
return [data].pack("H*")
|
48
|
+
end
|
49
|
+
|
50
|
+
def base58_encode(str, alphabet = :bitcoin)
|
51
|
+
Base58.binary_to_base58(str.force_encoding('BINARY'), alphabet)
|
52
|
+
end
|
53
|
+
|
54
|
+
def base58_decode(base58_str, alphabet = :bitcoin)
|
55
|
+
Base58.base58_to_binary(base58_str, alphabet)
|
56
|
+
end
|
57
|
+
|
58
|
+
end
|
59
|
+
|
60
|
+
end
|
data/lib/secp256k1zkp/version.rb
CHANGED
metadata
CHANGED
@@ -1,15 +1,29 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: secp256k1zkp
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.9.
|
4
|
+
version: 0.9.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- jokenshi
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2020-
|
11
|
+
date: 2020-10-21 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: base58
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: 0.2.3
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: 0.2.3
|
13
27
|
- !ruby/object:Gem::Dependency
|
14
28
|
name: mini_portile2
|
15
29
|
requirement: !ruby/object:Gem::Requirement
|
@@ -53,7 +67,7 @@ files:
|
|
53
67
|
- lib/secp256k1zkp/context.rb
|
54
68
|
- lib/secp256k1zkp/private_key.rb
|
55
69
|
- lib/secp256k1zkp/public_key.rb
|
56
|
-
- lib/secp256k1zkp/
|
70
|
+
- lib/secp256k1zkp/utility.rb
|
57
71
|
- lib/secp256k1zkp/version.rb
|
58
72
|
homepage: https://github.com/jokenshi/ruby-secp256zkp.git
|
59
73
|
licenses:
|
data/lib/secp256k1zkp/utils.rb
DELETED
@@ -1,20 +0,0 @@
|
|
1
|
-
#encoding:utf-8
|
2
|
-
|
3
|
-
require 'digest'
|
4
|
-
|
5
|
-
module Secp256k1Zkp
|
6
|
-
|
7
|
-
module Utils
|
8
|
-
|
9
|
-
module_function
|
10
|
-
|
11
|
-
#------------------------------------------------------------------------
|
12
|
-
# ● 计算sha1
|
13
|
-
#------------------------------------------------------------------------
|
14
|
-
def sha1(str)
|
15
|
-
return Digest::SHA1.hexdigest(str)
|
16
|
-
end
|
17
|
-
|
18
|
-
end
|
19
|
-
|
20
|
-
end
|