Skip to content

Commit 6c1ef72

Browse files
authored
feat(protocol): Added configuration part for all network shapes of Handshake protocol (#396)
Signed-off-by: Akhil Repala <arepala@blinklabs.io>
1 parent d5d9e42 commit 6c1ef72

File tree

1 file changed

+355
-0
lines changed

1 file changed

+355
-0
lines changed
Lines changed: 355 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,355 @@
1+
package protocol
2+
3+
// Shapes only - constants & configs from hsd's protocol/networks.js.
4+
5+
import (
6+
"math/big"
7+
"sort"
8+
"strings"
9+
"sync"
10+
"time"
11+
)
12+
13+
type NetworkType string
14+
15+
const (
16+
Mainnet NetworkType = "main"
17+
Testnet NetworkType = "testnet"
18+
Regtest NetworkType = "regtest"
19+
Simnet NetworkType = "simnet"
20+
)
21+
22+
type TimeSource interface {
23+
Now() time.Time
24+
Ms() int64
25+
}
26+
27+
type systemTime struct{}
28+
29+
func (t *systemTime) Now() time.Time {
30+
return time.Now()
31+
}
32+
33+
func (t *systemTime) Ms() int64 {
34+
return time.Now().UnixMilli()
35+
}
36+
37+
type Checkpoint struct {
38+
Height uint32
39+
Hash string
40+
}
41+
42+
type Deployment struct {
43+
Name string
44+
Bit uint32
45+
StartTime uint32
46+
Timeout uint32
47+
Threshold int32
48+
Window int32
49+
Required bool
50+
Force bool
51+
}
52+
53+
type KeyPrefix struct {
54+
Privkey uint32
55+
XPubKey uint32
56+
XPrivKey uint32
57+
XPubKey58 string
58+
XPrivKey58 string
59+
CoinType uint32
60+
}
61+
62+
type POWParams struct {
63+
Limit *big.Int
64+
Bits uint32
65+
Chainwork *big.Int
66+
TargetWindow uint32
67+
TargetSpacing uint32
68+
BlocksPerDay uint32
69+
TargetTimespan uint32
70+
MinActual uint32
71+
MaxActual uint32
72+
TargetReset bool
73+
NoRetargeting bool
74+
}
75+
76+
type BlockLimits struct {
77+
PruneAfterHeight uint32
78+
KeepBlocks uint32
79+
MaxTipAge uint32
80+
SlowHeight uint32
81+
}
82+
83+
type NamesParams struct {
84+
AuctionStart uint32
85+
RolloutInterval uint32
86+
LockupPeriod uint32
87+
RenewalWindow uint32
88+
RenewalPeriod uint32
89+
RenewalMaturity uint32
90+
ClaimPeriod uint32
91+
AlexaLockupPeriod uint32
92+
ClaimFrequency uint32
93+
BiddingPeriod uint32
94+
RevealPeriod uint32
95+
TreeInterval uint32
96+
TransferLockup uint32
97+
AuctionMaturity uint32
98+
NoRollout bool
99+
NoReserved bool
100+
}
101+
102+
type Network struct {
103+
Type string
104+
Seeds []string
105+
Magic uint32
106+
Port uint16
107+
BrontidePort uint16
108+
CheckpointMap map[uint32]string
109+
LastCheckpoint uint32
110+
Checkpoints []Checkpoint
111+
112+
HalvingInterval uint32
113+
CoinbaseMaturity uint32
114+
GenesisHash string
115+
GenesisBlockHex string
116+
UnknownBitsMask uint32
117+
118+
POW POWParams
119+
Names NamesParams
120+
GoosigStop uint32
121+
Block BlockLimits
122+
123+
ActivationThreshold uint32
124+
MinerWindow uint32
125+
126+
Deployments map[string]Deployment
127+
Deploys []Deployment
128+
129+
KeyPrefix KeyPrefix
130+
AddressPrefix string
131+
ClaimPrefix string
132+
133+
RequireStandard bool
134+
MinRelay uint32
135+
FeeRate uint32
136+
MaxFeeRate uint32
137+
138+
RPCPort uint16
139+
WalletPort uint16
140+
NSPort uint16
141+
RSPort uint16
142+
143+
IdentityKeyHex string
144+
SelfConnect bool
145+
RequestMempool bool
146+
147+
DeflationHeight uint32
148+
TxStartHeight uint32
149+
timeSource TimeSource
150+
onceInit sync.Once
151+
}
152+
153+
func (n *Network) init() {
154+
n.onceInit.Do(func() {
155+
if n.timeSource == nil {
156+
n.timeSource = &systemTime{}
157+
}
158+
var mask uint32
159+
for _, d := range n.Deploys {
160+
if d.Bit < 32 {
161+
mask |= (1 << d.Bit)
162+
}
163+
}
164+
n.UnknownBitsMask = ^mask
165+
n.Checkpoints = n.checkpointsFromMap()
166+
sort.Slice(n.Checkpoints, func(i, j int) bool {
167+
return n.Checkpoints[i].Height < n.Checkpoints[j].Height
168+
})
169+
})
170+
}
171+
172+
func (n *Network) checkpointsFromMap() []Checkpoint {
173+
if len(n.CheckpointMap) == 0 {
174+
return nil
175+
}
176+
out := make([]Checkpoint, 0, len(n.CheckpointMap))
177+
for h, hash := range n.CheckpointMap {
178+
out = append(out, Checkpoint{Height: h, Hash: strings.ToLower(hash)})
179+
}
180+
return out
181+
}
182+
183+
func (n *Network) ByBit(bit uint32) *Deployment {
184+
for i := range n.Deploys {
185+
if n.Deploys[i].Bit == bit {
186+
return &n.Deploys[i]
187+
}
188+
}
189+
return nil
190+
}
191+
192+
func (n *Network) ensureTime() {
193+
if n.timeSource == nil {
194+
n.timeSource = &systemTime{}
195+
}
196+
}
197+
198+
func (n *Network) SetTimeSource(ts TimeSource) {
199+
n.timeSource = ts
200+
}
201+
202+
func (n *Network) Now() time.Time {
203+
n.ensureTime()
204+
return n.timeSource.Now()
205+
}
206+
207+
func (n *Network) Ms() int64 {
208+
n.ensureTime()
209+
return n.timeSource.Ms()
210+
}
211+
212+
func bi(hex string) *big.Int {
213+
n := new(big.Int)
214+
if _, ok := n.SetString(hex, 16); !ok {
215+
panic("invalid hex for big.Int: " + hex)
216+
}
217+
return n
218+
}
219+
220+
var Networks = map[NetworkType]*Network{
221+
Mainnet: mainNet(),
222+
Testnet: testNet(),
223+
Regtest: regTest(),
224+
Simnet: simNet(),
225+
}
226+
227+
func SelectNetwork(t NetworkType) *Network {
228+
return Networks[t]
229+
}
230+
231+
func testNet() *Network {
232+
const (
233+
targetSpacing = uint32(10 * 60)
234+
targetWindow = uint32(144)
235+
)
236+
blocksPerDay := uint32((24 * 60 * 60) / targetSpacing)
237+
targetTimespan := targetWindow * targetSpacing
238+
239+
n := &Network{
240+
Type: "testnet",
241+
Seeds: []string{"hs-testnet.bcoin.ninja"},
242+
Magic: 0, // Need to modify from genesis.testnet.magic
243+
Port: 13038,
244+
BrontidePort: 45806,
245+
246+
CheckpointMap: map[uint32]string{},
247+
LastCheckpoint: 0,
248+
249+
HalvingInterval: 170000,
250+
CoinbaseMaturity: 100,
251+
252+
POW: POWParams{
253+
Limit: bi("00000000ffff0000000000000000000000000000000000000000000000000000"),
254+
Bits: 0x1d00ffff,
255+
Chainwork: bi("0000000000000000000000000000000000000000000000000000000000000000"),
256+
TargetWindow: targetWindow,
257+
TargetSpacing: targetSpacing,
258+
BlocksPerDay: blocksPerDay,
259+
TargetTimespan: targetTimespan,
260+
MinActual: targetTimespan / 4,
261+
MaxActual: targetTimespan * 4,
262+
TargetReset: true,
263+
NoRetargeting: false,
264+
},
265+
266+
Names: NamesParams{
267+
AuctionStart: uint32(0.25 * float32(blocksPerDay)),
268+
RolloutInterval: uint32(0.25 * float32(blocksPerDay)),
269+
LockupPeriod: uint32(0.25 * float32(blocksPerDay)),
270+
RenewalWindow: 30 * blocksPerDay,
271+
RenewalPeriod: 7 * blocksPerDay,
272+
RenewalMaturity: 1 * blocksPerDay,
273+
ClaimPeriod: 90 * blocksPerDay,
274+
AlexaLockupPeriod: 180 * blocksPerDay,
275+
ClaimFrequency: 2 * blocksPerDay,
276+
BiddingPeriod: 1 * blocksPerDay,
277+
RevealPeriod: 2 * blocksPerDay,
278+
TreeInterval: blocksPerDay >> 2,
279+
TransferLockup: 2 * blocksPerDay,
280+
AuctionMaturity: (1 + 2 + 4) * blocksPerDay,
281+
NoRollout: false,
282+
NoReserved: false,
283+
},
284+
285+
Block: BlockLimits{
286+
PruneAfterHeight: 1000,
287+
KeepBlocks: 10000,
288+
MaxTipAge: 12 * 60 * 60,
289+
SlowHeight: 0,
290+
},
291+
292+
GoosigStop: 20 * blocksPerDay,
293+
ActivationThreshold: 1512,
294+
MinerWindow: 2016,
295+
296+
Deployments: map[string]Deployment{
297+
"hardening": {Name: "hardening", Bit: 0, StartTime: 1581638400, Timeout: 1707868800, Threshold: -1, Window: -1, Required: false, Force: false},
298+
"icannlockup": {Name: "icannlockup", Bit: 1, StartTime: 1691625600, Timeout: 1703980800, Threshold: -1, Window: -1, Required: false, Force: false},
299+
"airstop": {Name: "airstop", Bit: 2, StartTime: 1751328000, Timeout: 1759881600, Threshold: -1, Window: -1, Required: false, Force: false},
300+
"testdummy": {Name: "testdummy", Bit: 28, StartTime: 1199145601, Timeout: 1230767999, Threshold: -1, Window: -1, Required: false, Force: true},
301+
},
302+
Deploys: []Deployment{
303+
{Name: "hardening", Bit: 0, StartTime: 1581638400, Timeout: 1707868800, Threshold: -1, Window: -1, Required: false, Force: false},
304+
{Name: "icannlockup", Bit: 1, StartTime: 1691625600, Timeout: 1703980800, Threshold: -1, Window: -1, Required: false, Force: false},
305+
{Name: "airstop", Bit: 2, StartTime: 1751328000, Timeout: 1759881600, Threshold: -1, Window: -1, Required: false, Force: false},
306+
{Name: "testdummy", Bit: 28, StartTime: 1199145601, Timeout: 1230767999, Threshold: -1, Window: -1, Required: false, Force: true},
307+
},
308+
309+
KeyPrefix: KeyPrefix{
310+
Privkey: 0xef,
311+
XPubKey: 0x043587cf,
312+
XPrivKey: 0x04358394,
313+
XPubKey58: "tpub",
314+
XPrivKey58: "tprv",
315+
CoinType: 5354,
316+
},
317+
AddressPrefix: "ts",
318+
ClaimPrefix: "hns-testnet:",
319+
RequireStandard: false,
320+
321+
RPCPort: 13037,
322+
WalletPort: 13039,
323+
NSPort: 15349,
324+
RSPort: 15350,
325+
326+
MinRelay: 1000,
327+
FeeRate: 20000,
328+
MaxFeeRate: 60000,
329+
330+
IdentityKeyHex: "",
331+
SelfConnect: false,
332+
RequestMempool: true,
333+
334+
DeflationHeight: 0,
335+
TxStartHeight: 0,
336+
}
337+
n.ensureTime()
338+
n.init()
339+
return n
340+
}
341+
342+
func mainNet() *Network {
343+
// Need to implement
344+
return &Network{}
345+
}
346+
347+
func regTest() *Network {
348+
// Need to implement
349+
return &Network{}
350+
}
351+
352+
func simNet() *Network {
353+
// Need to implement
354+
return &Network{}
355+
}

0 commit comments

Comments
 (0)