git.frostfs.info/TrueCloudLab/frostfs-sdk-go@v0.0.0-20241022124111-5361f0ecebd3/crypto/signature.go (about) 1 package frostfscrypto 2 3 import ( 4 "errors" 5 "fmt" 6 7 "git.frostfs.info/TrueCloudLab/frostfs-api-go/v2/refs" 8 ) 9 10 // Signature represents a confirmation of data integrity received by the 11 // digital signature mechanism. 12 // 13 // Signature is mutually compatible with git.frostfs.info/TrueCloudLab/frostfs-api-go/v2/refs.Signature 14 // message. See ReadFromV2 / WriteToV2 methods. 15 // 16 // Note that direct typecast is not safe and may result in loss of compatibility: 17 // 18 // _ = Signature(refs.Signature{}) // not recommended 19 type Signature refs.Signature 20 21 // ReadFromV2 reads Signature from the refs.Signature message. Checks if the 22 // message conforms to FrostFS API V2 protocol. 23 // 24 // See also WriteToV2. 25 func (x *Signature) ReadFromV2(m refs.Signature) error { 26 if len(m.GetKey()) == 0 { 27 return errors.New("missing public key") 28 } else if len(m.GetSign()) == 0 { 29 return errors.New("missing signature") 30 } 31 32 switch m.GetScheme() { 33 default: 34 return fmt.Errorf("unsupported scheme %v", m.GetSign()) 35 case 36 refs.ECDSA_SHA512, 37 refs.ECDSA_RFC6979_SHA256, 38 refs.ECDSA_RFC6979_SHA256_WALLET_CONNECT: 39 } 40 41 *x = Signature(m) 42 43 return nil 44 } 45 46 // WriteToV2 writes Signature to the refs.Signature message. 47 // The message must not be nil. 48 // 49 // See also ReadFromV2. 50 func (x Signature) WriteToV2(m *refs.Signature) { 51 *m = (refs.Signature)(x) 52 } 53 54 // Calculate signs data using Signer and encodes public key for subsequent 55 // verification. 56 // 57 // Signer MUST NOT be nil. 58 // 59 // See also Verify. 60 func (x *Signature) Calculate(signer Signer, data []byte) error { 61 signature, err := signer.Sign(data) 62 if err != nil { 63 return fmt.Errorf("signer %T failure: %w", signer, err) 64 } 65 66 pub := signer.Public() 67 68 key := make([]byte, pub.MaxEncodedSize()) 69 key = key[:pub.Encode(key)] 70 71 m := (*refs.Signature)(x) 72 73 m.SetScheme(refs.SignatureScheme(signer.Scheme())) 74 m.SetSign(signature) 75 m.SetKey(key) 76 77 return nil 78 } 79 80 // Verify verifies data signature using encoded public key. True means valid 81 // signature. 82 // 83 // Verify fails if signature scheme is not supported (see RegisterScheme). 84 // 85 // See also Calculate. 86 func (x Signature) Verify(data []byte) bool { 87 m := (*refs.Signature)(&x) 88 89 f, ok := publicKeys[Scheme(m.GetScheme())] 90 if !ok { 91 return false 92 } 93 94 key := f() 95 96 err := key.Decode(m.GetKey()) 97 if err != nil { 98 return false 99 } 100 101 return key.Verify(data, m.GetSign()) 102 }