This repository has been archived by the owner on Mar 7, 2023. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 0
/
api.go
106 lines (91 loc) · 2.78 KB
/
api.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
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
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
package dpcc
import (
"errors"
"github.com/si-co/dpcc/lib"
"go.dedis.ch/cothority/v3"
"go.dedis.ch/onet/v3"
"go.dedis.ch/onet/v3/log"
)
// ServiceName is used for registration on the onet.
const ServiceName = "DPPC"
// Client is a structure to communicate with the DWC
// service
type Client struct {
*onet.Client
}
// NewClient instantiates a new decenarch.Client
func NewClient() *Client {
return &Client{Client: onet.NewClient(cothority.Suite, ServiceName)}
}
// PublicHashRequest sends a request for a public hash protocol to the roster
func (c *Client) PublicHashRequest(r *onet.Roster, URL string) (*HashPublicResponse, error) {
// verify the roster
if len(r.List) == 0 {
return nil, errors.New("got an empty roster list")
}
// prepare request for the leader
req := &HashPublicRequest{
Roster: r,
URL: URL,
Nonce: lib.GenNonce(),
}
// send request to a random conode in the roster, acting as the leader
// of the protocol
dst := r.RandomServerIdentity()
log.Lvl4("sending message to leader", dst)
resp := &HashPublicResponse{}
err := c.SendProtobuf(dst, req, resp)
if err != nil {
return nil, err
}
return resp, nil
}
// PrivateHashRequest sends a request for a private hash protocol to the roster
func (c *Client) PrivateHashRequest(r *onet.Roster, URL string) (*HashPrivateResponse, error) {
// verify the roster
if len(r.List) == 0 {
return nil, errors.New("got an empty roster list")
}
// generate ephemeral keys. Note: this has to be done here on the
// client, because in this setting the leader is considered to be HBC
// and therefore we don't want him to be able to decrypt the hashes
privateKeys, publicKeys := lib.GenEphemeralKeys(r)
// prepare request for the leader
req := &HashPrivateRequest{
Roster: r,
URL: URL,
ClientPublicKeys: publicKeys,
}
// send request to a random conode in the roster, acting as the leader
// of the protocol
dst := r.RandomServerIdentity()
log.Lvl4("sending message to leader", dst)
resp := &HashPrivateResponse{}
err := c.SendProtobuf(dst, req, resp)
if err != nil {
return nil, err
}
// decrypt the received hashes
hashes := make(map[string][]byte)
for pk, v := range resp.Responses {
// compute previsously shared key
pre := lib.DhExchange(privateKeys[pk], v.PublicKey)
// determine context for this AEAD scheme
ctx := lib.Context(publicKeys[pk], v.PublicKey)
// instantiate AEAD scheme (AES128-GCM)
gcm, err := lib.NewAEAD(cothority.Suite.Hash, pre, ctx)
if err != nil {
return nil, err
}
// encrypt hash with AES128-GCM
decrypted, err := gcm.Open(nil, v.Nonce, v.EncryptedHash, nil)
if err != nil {
return nil, err
}
// store decrypted hash
hashes[pk] = decrypted
}
// send decrypted hashes back to the app
resp.Hashes = hashes
return resp, nil
}