https://github.com/bnb-chain/tss-lib
Threshold Signature Scheme, for ECDSA and EDDSA
Science Score: 26.0%
This score indicates how likely this project is to be science-related based on various indicators:
-
○CITATION.cff file
-
✓codemeta.json file
Found codemeta.json file -
✓.zenodo.json file
Found .zenodo.json file -
○DOI references
-
○Academic publication links
-
○Committers with academic emails
-
○Institutional organization owner
-
○JOSS paper metadata
-
○Scientific vocabulary similarity
Low similarity (11.7%) to scientific vocabulary
Keywords
Repository
Threshold Signature Scheme, for ECDSA and EDDSA
Basic Info
Statistics
- Stars: 906
- Watchers: 32
- Forks: 321
- Open Issues: 68
- Releases: 0
Topics
Metadata Files
README.md
Multi-Party Threshold Signature Scheme
Permissively MIT Licensed.
Note! This is a library for developers. You may find a TSS tool that you can use with the Binance Chain CLI here.
Introduction
This is an implementation of multi-party {t,n}-threshold ECDSA (Elliptic Curve Digital Signature Algorithm) based on Gennaro and Goldfeder CCS 2018 1 and EdDSA (Edwards-curve Digital Signature Algorithm) following a similar approach.
This library includes three protocols:
- Key Generation for creating secret shares with no trusted dealer ("keygen").
- Signing for using the secret shares to generate a signature ("signing").
- Dynamic Groups to change the group of participants while keeping the secret ("resharing").
⚠️ Do not miss these important notes on implementing this library securely
Rationale
ECDSA is used extensively for crypto-currencies such as Bitcoin, Ethereum (secp256k1 curve), NEO (NIST P-256 curve) and many more.
EdDSA is used extensively for crypto-currencies such as Cardano, Aeternity, Stellar Lumens and many more.
For such currencies this technique may be used to create crypto wallets where multiple parties must collaborate to sign transactions. See MultiSig Use Cases
One secret share per key/address is stored locally by each participant and these are kept safe by the protocol – they are never revealed to others at any time. Moreover, there is no trusted dealer of the shares.
In contrast to MultiSig solutions, transactions produced by TSS preserve the privacy of the signers by not revealing which t+1 participants were involved in their signing.
There is also a performance bonus in that blockchain nodes may check the validity of a signature without any extra MultiSig logic or processing.
Usage
You should start by creating an instance of a LocalParty and giving it the arguments that it needs.
The LocalParty that you use should be from the keygen, signing or resharing package depending on what you want to do.
Setup
```go // When using the keygen party it is recommended that you pre-compute the "safe primes" and Paillier secret beforehand because this can take some time. // This code will generate those parameters using a concurrency limit equal to the number of available CPU cores. preParams, _ := keygen.GeneratePreParams(1 * time.Minute)
// Create a *PartyID for each participating peer on the network (you should call tss.NewPartyID for each one)
parties := tss.SortPartyIDs(getParticipantPartyIDs())
// Set up the parameters
// Note: The id and moniker fields are for convenience to allow you to easily track participants.
// The id should be a unique string representing this party in the network and moniker can be anything (even left blank).
// The uniqueKey is a unique identifying key for this peer (such as its p2p public key) as a big.Int.
thisParty := tss.NewPartyID(id, moniker, uniqueKey)
ctx := tss.NewPeerContext(parties)
// Select an elliptic curve // use ECDSA curve := tss.S256() // or use EdDSA // curve := tss.Edwards()
params := tss.NewParameters(curve, ctx, thisParty, len(parties), threshold)
// You should keep a local mapping of id strings to *PartyID instances so that an incoming message can have its origin party's *PartyID recovered for passing to UpdateFromBytes (see below)
partyIDMap := make(map[string]*PartyID)
for _, id := range parties {
partyIDMap[id.Id] = id
}
```
Keygen
Use the keygen.LocalParty for the keygen protocol. The save data you receive through the endCh upon completion of the protocol should be persisted to secure storage.
go
party := keygen.NewLocalParty(params, outCh, endCh, preParams) // Omit the last arg to compute the pre-params in round 1
go func() {
err := party.Start()
// handle err ...
}()
Signing
Use the signing.LocalParty for signing and provide it with a message to sign. It requires the key data obtained from the keygen protocol. The signature will be sent through the endCh once completed.
Please note that t+1 signers are required to sign a message and for optimal usage no more than this should be involved. Each signer should have the same view of who the t+1 signers are.
go
party := signing.NewLocalParty(message, params, ourKeyData, outCh, endCh)
go func() {
err := party.Start()
// handle err ...
}()
Re-Sharing
Use the resharing.LocalParty to re-distribute the secret shares. The save data received through the endCh should overwrite the existing key data in storage, or write new data if the party is receiving a new share.
Please note that ReSharingParameters is used to give this Party more context about the re-sharing that should be carried out.
go
party := resharing.NewLocalParty(params, ourKeyData, outCh, endCh)
go func() {
err := party.Start()
// handle err ...
}()
⚠️ During re-sharing the key data may be modified during the rounds. Do not ever overwrite any data saved on disk until the final struct has been received through the end channel.
Messaging
In these examples the outCh will collect outgoing messages from the party and the endCh will receive save data or a signature when the protocol is complete.
During the protocol you should provide the party with updates received from other participating parties on the network.
A Party has two thread-safe methods on it for receiving updates.
go
// The main entry point when updating a party's state from the wire
UpdateFromBytes(wireBytes []byte, from *tss.PartyID, isBroadcast bool) (ok bool, err *tss.Error)
// You may use this entry point to update a party's state when running locally or in tests
Update(msg tss.ParsedMessage) (ok bool, err *tss.Error)
And a tss.Message has the following two methods for converting messages to data for the wire:
go
// Returns the encoded message bytes to send over the wire along with routing information
WireBytes() ([]byte, *tss.MessageRouting, error)
// Returns the protobuf wrapper message struct, used only in some exceptional scenarios (i.e. mobile apps)
WireMsg() *tss.MessageWrapper
In a typical use case, it is expected that a transport implementation will consume message bytes via the out channel of the local Party, send them to the destination(s) specified in the result of msg.GetTo(), and pass them to UpdateFromBytes on the receiving end.
This way there is no need to deal with Marshal/Unmarshalling Protocol Buffers to implement a transport.
Changes of Preparams of ECDSA in v2.0
Two fields PaillierSK.P and PaillierSK.Q is added in version 2.0. They are used to generate Paillier key proofs. Key valuts generated from versions before 2.0 need to regenerate(resharing) the key valuts to update the praparams with the necessary fileds filled.
How to use this securely
⚠️ This section is important. Be sure to read it!
The transport for messaging is left to the application layer and is not provided by this library. Each one of the following paragraphs should be read and followed carefully as it is crucial that you implement a secure transport to ensure safety of the protocol.
When you build a transport, it should offer a broadcast channel as well as point-to-point channels connecting every pair of parties. Your transport should also employ suitable end-to-end encryption (TLS with an AEAD cipher is recommended) between parties to ensure that a party can only read the messages sent to it.
Within your transport, each message should be wrapped with a session ID that is unique to a single run of the keygen, signing or re-sharing rounds. This session ID should be agreed upon out-of-band and known only by the participating parties before the rounds begin. Upon receiving any message, your program should make sure that the received session ID matches the one that was agreed upon at the start.
Additionally, there should be a mechanism in your transport to allow for "reliable broadcasts", meaning parties can broadcast a message to other parties such that it's guaranteed that each one receives the same message. There are several examples of algorithms online that do this by sharing and comparing hashes of received messages.
Timeouts and errors should be handled by your application. The method WaitingFor may be called on a Party to get the set of other parties that it is still waiting for messages from. You may also get the set of culprit parties that caused an error from a *tss.Error.
Security Audit
A full review of this library was carried out by Kudelski Security and their final report was made available in October, 2019. A copy of this report audit-binance-tss-lib-final-20191018.pdf may be found in the v1.0.0 release notes of this repository.
References
[1] https://eprint.iacr.org/2019/114.pdf
Owner
- Name: bnb-chain
- Login: bnb-chain
- Kind: organization
- Website: https://www.bnbchain.org
- Twitter: BNBChain
- Repositories: 99
- Profile: https://github.com/bnb-chain
For BNB Chain: BNB Smart Chain, BNB Beacon Chain
GitHub Events
Total
- Issues event: 7
- Watch event: 130
- Issue comment event: 13
- Push event: 3
- Pull request event: 7
- Fork event: 49
- Create event: 1
Last Year
- Issues event: 7
- Watch event: 130
- Issue comment event: 13
- Push event: 3
- Pull request event: 7
- Fork event: 49
- Create event: 1
Committers
Last synced: 9 months ago
Top Committers
| Name | Commits | |
|---|---|---|
| Luke Plaster | me@l****g | 272 |
| Cong Zhao | z****9@g****m | 39 |
| ycen | y****n@l****m | 20 |
| HAOYUatHZ | 3****Z | 5 |
| Moein zargarzadeh | m****h@g****m | 5 |
| Plamen Hristov | p****v@b****d | 5 |
| zhiqiangxu | 6****0@q****m | 4 |
| Piotr Dyraga | p****a@k****k | 4 |
| yutianwu | w****t@g****m | 2 |
| ZhAnGeek | 3****k | 2 |
| Sun Xia | a****x@g****m | 2 |
| FitzLu | l****g@b****m | 1 |
| Guilherme Versiani | g****i@G****l | 1 |
| Fitz | 4****u | 1 |
| HAOYUatHZ | h****u@p****m | 1 |
| Oleg Fomenko | 3****o | 1 |
| Pablo Lopez | p****z@g****m | 1 |
| dylenfu | d****u@1****m | 1 |
| typestring | 2****g | 1 |
| xiaoguang-binance | 4****e | 1 |
Committer Domains (Top 20 + Academic)
Issues and Pull Requests
Last synced: 6 months ago
All Time
- Total issues: 105
- Total pull requests: 79
- Average time to close issues: 8 months
- Average time to close pull requests: 9 months
- Total issue authors: 75
- Total pull request authors: 29
- Average comments per issue: 1.84
- Average comments per pull request: 1.22
- Merged pull requests: 37
- Bot issues: 0
- Bot pull requests: 0
Past Year
- Issues: 9
- Pull requests: 6
- Average time to close issues: 1 day
- Average time to close pull requests: 1 minute
- Issue authors: 7
- Pull request authors: 4
- Average comments per issue: 0.56
- Average comments per pull request: 0.0
- Merged pull requests: 0
- Bot issues: 0
- Bot pull requests: 0
Top Authors
Issue Authors
- neciriye (5)
- zargarzadehm (4)
- Aseyed (4)
- r4881t (4)
- daryakaviani (3)
- kolvin2016 (3)
- gojuukaze (3)
- HAOYUatHZ (2)
- lucky1024 (2)
- zergweak (2)
- misaqsaadat (2)
- typestring (2)
- jpopxfile (2)
- notatestuser (2)
- daevontkhplanesw (2)
Pull Request Authors
- yycen (24)
- Debu976116 (11)
- froyobin (9)
- ackratos (6)
- zhiqiangxu (6)
- HAOYUatHZ (4)
- asdfsx (4)
- felicityin (3)
- pdyraga (3)
- aeroxy (3)
- balena (2)
- gartnera (2)
- ZhAnGeek (2)
- timoftime (2)
- smiletrl (2)
Top Labels
Issue Labels
Pull Request Labels
Packages
- Total packages: 2
- Total downloads: unknown
- Total docker downloads: 2,156
-
Total dependent packages: 14
(may contain duplicates) -
Total dependent repositories: 6
(may contain duplicates) - Total versions: 13
- Total advisories: 5
proxy.golang.org: github.com/bnb-chain/tss-lib
- Homepage: https://github.com/bnb-chain/tss-lib
- Documentation: https://pkg.go.dev/github.com/bnb-chain/tss-lib#section-documentation
- License: MIT
-
Latest release: v1.5.0
published over 2 years ago
Rankings
Advisories (5)
- IO FinNet tss-lib vulnerable to timing attack from non-constant time scalar arithmetic
- tss-lib leaks secret keys in response to incorrectly constructed Paillier moduli
- IO FinNet tss-lib vulnerable to replay attacks involving proofs
- Collision of hash values in github.com/bnb-chain/tss-lib
- IO FinNet tss-lib vulnerable to timing attack from non-constant time scalar multiplication
proxy.golang.org: github.com/bnb-chain/tss-lib/v2
- Homepage: https://github.com/bnb-chain/tss-lib
- Documentation: https://pkg.go.dev/github.com/bnb-chain/tss-lib/v2#section-documentation
- License: MIT
-
Latest release: v2.0.2
published about 2 years ago