Module: BTC::Secp256k1

Extended by:
Secp256k1
Includes:
FFI::Library
Included in:
Secp256k1
Defined in:
lib/btcruby/secp256k1.rb

Overview

Bindings to Pieter Wuille's libsecp256k1. This is not included by default, to enable use: require 'btcruby/secp256k1'

Defined Under Namespace

Classes: Signature

Constant Summary collapse

SECP256K1_FLAGS_TYPE_CONTEXT =
(1 << 0)
SECP256K1_FLAGS_BIT_CONTEXT_VERIFY =
(1 << 8)
SECP256K1_FLAGS_BIT_CONTEXT_SIGN =
(1 << 9)
SECP256K1_CONTEXT_SIGN =
(SECP256K1_FLAGS_TYPE_CONTEXT | SECP256K1_FLAGS_BIT_CONTEXT_SIGN)

Instance Method Summary collapse

Instance Method Details

#ecdsa_signature(hash, privkey) ⇒ Object

Raises:

  • (ArgumentError)


34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
# File 'lib/btcruby/secp256k1.rb', line 34

def ecdsa_signature(hash, privkey)
  raise ArgumentError, "Hash is missing" if !hash
  raise ArgumentError, "Private key is missing" if !privkey
  
  with_context(SECP256K1_CONTEXT_SIGN) do |ctx|
    hash_buf = FFI::MemoryPointer.new(:uchar, hash.bytesize)
    hash_buf.put_bytes(0, hash)

    sig = Signature.new

    privkey_buf = FFI::MemoryPointer.new(:uchar, privkey.bytesize)
    privkey_buf.put_bytes(0, privkey)
    
    if secp256k1_ecdsa_sign(ctx, sig.pointer, hash_buf, privkey_buf, nil, nil) == 1
      # Serialize an ECDSA signature in DER format.
      bufsize = 72
      output_pointer = FFI::MemoryPointer.new(:uint8, bufsize)
      outputlen_pointer = FFI::MemoryPointer.new(:uint).put_uint(0, bufsize)
      if secp256k1_ecdsa_signature_serialize_der(ctx, output_pointer, outputlen_pointer, sig.pointer) == 1
        actual_length = outputlen_pointer.read_uint
        return output_pointer.read_string(actual_length)
      end
    end
    return nil
  end
end

#ecdsa_verify(signature, hash, public_key) ⇒ Object

Raises:

  • (ArgumentError)


61
62
63
64
65
66
67
# File 'lib/btcruby/secp256k1.rb', line 61

def ecdsa_verify(signature, hash, public_key)
  raise ArgumentError, "Signature is missing" if !signature
  raise ArgumentError, "Hash is missing" if !hash
  raise ArgumentError, "Public key is missing" if !public_key
  
  # TODO:...
end

#with_context(options = 0) ⇒ Object



69
70
71
72
73
74
75
76
# File 'lib/btcruby/secp256k1.rb', line 69

def with_context(options = 0)
  begin
    ctx = secp256k1_context_create(options)
    yield(ctx)
  ensure
    secp256k1_context_destroy(ctx)
  end
end