Commit 419e3f2a authored by David Vorick's avatar David Vorick

Merge branch 'last-135' into 'master'

prepare for ASIC hardfork

See merge request !3282
parents 601b3fc4 63cb6005
Pipeline #33168714 failed with stages
in 28 minutes and 11 seconds
Version History
---------------
Oct 2018:
v1.3.5 (patch release)
- Add offline signing functionality
- Overhaul hostdb weighting
- Add siac utils
Sep 2018:
v1.3.4 (patch release)
......
......@@ -244,7 +244,7 @@ func (srv *Server) daemonUpdateHandlerGET(w http.ResponseWriter, _ *http.Request
}
latestVersion := release.TagName[1:] // delete leading 'v'
api.WriteJSON(w, UpdateInfo{
Available: build.VersionCmp(latestVersion, build.Version) > 0,
Available: build.VersionCmp(latestVersion, build.Version) > 0 && false,
Version: latestVersion,
})
}
......
......@@ -2,6 +2,7 @@ package consensus
import (
"bytes"
"encoding/binary"
"errors"
"fmt"
"os"
......@@ -107,6 +108,10 @@ func (cs *ConsensusSet) validateHeader(tx dbTx, h types.BlockHeader) error {
return err
}
// Check that the nonce is a legal nonce.
if parent.Height >= types.ASICHardforkHeight && binary.LittleEndian.Uint64(h.Nonce[:])%types.ASICHardforkFactor != 0 {
return errors.New("block does not meet nonce requirements")
}
// Check that the target of the new block is sufficient.
if !checkHeaderTarget(h, parent.ChildTarget) {
return modules.ErrBlockUnsolved
......@@ -291,7 +296,6 @@ func (cs *ConsensusSet) managedAcceptBlocks(blocks []types.Block) (blockchainExt
}
if setErr != nil {
if len(changes) == 0 {
fmt.Println("Received an invalid block set.")
cs.log.Println("Consensus received an invalid block:", setErr)
} else {
fmt.Println("Received a partially valid block set.")
......
......@@ -5,6 +5,7 @@ import (
"errors"
"testing"
"time"
"unsafe"
"gitlab.com/NebulousLabs/Sia/modules"
"gitlab.com/NebulousLabs/Sia/persist"
......@@ -645,8 +646,8 @@ func TestMissedTarget(t *testing.T) {
if err != nil {
t.Fatal(err)
}
for checkTarget(block, block.ID(), target) && block.Nonce[0] != 255 {
block.Nonce[0]++
for checkTarget(block, block.ID(), target) {
*(*uint64)(unsafe.Pointer(&block.Nonce)) += types.ASICHardforkFactor
}
if checkTarget(block, block.ID(), target) {
t.Fatal("unable to find a failing target")
......
......@@ -2,6 +2,7 @@ package consensus
import (
"bytes"
"encoding/binary"
"errors"
"gitlab.com/NebulousLabs/Sia/modules"
......@@ -69,6 +70,10 @@ func (bv stdBlockValidator) ValidateBlock(b types.Block, id types.BlockID, minTi
return errEarlyTimestamp
}
// Check that the nonce is a legal nonce.
if height >= types.ASICHardforkHeight && binary.LittleEndian.Uint64(b.Nonce[:])%types.ASICHardforkFactor != 0 {
return errors.New("block does not meet nonce requirements")
}
// Check that the target of the new block is sufficient.
if !checkTarget(b, id, target) {
return modules.ErrBlockUnsolved
......
......@@ -3,6 +3,7 @@ package miner
import (
"bytes"
"testing"
"unsafe"
"gitlab.com/NebulousLabs/Sia/crypto"
"gitlab.com/NebulousLabs/Sia/modules"
......@@ -17,7 +18,7 @@ func solveHeader(header types.BlockHeader, target types.Target) types.BlockHeade
for {
// Increment the nonce first to guarantee that a new header is formed
// - this helps check for pointer errors.
header.Nonce[0]++
*(*uint64)(unsafe.Pointer(&header.Nonce)) += types.ASICHardforkFactor
id := crypto.HashObject(header)
if bytes.Compare(target[:], id[:]) >= 0 {
break
......
......@@ -5,6 +5,7 @@ import (
"path/filepath"
"testing"
"time"
"unsafe"
"gitlab.com/NebulousLabs/Sia/build"
"gitlab.com/NebulousLabs/Sia/crypto"
......@@ -173,10 +174,10 @@ func TestIntegrationBlocksMined(t *testing.T) {
if err != nil {
t.Fatal(err)
}
// Unsolve the header - necessary because the target is very low when
// Solve the header - necessary because the target is very low when
// mining.
for {
unsolvedHeader.Nonce[0]++
*(*uint64)(unsafe.Pointer(&unsolvedHeader.Nonce)) += types.ASICHardforkFactor
id := crypto.HashObject(unsolvedHeader)
if bytes.Compare(target[:], id[:]) < 0 {
break
......
......@@ -39,7 +39,7 @@ func solveBlock(b types.Block, target types.Target) (types.Block, bool) {
return b, true
}
*(*uint64)(unsafe.Pointer(&header[32])) = nonce
nonce++
nonce += types.ASICHardforkFactor
}
return b, false
}
......
......@@ -175,6 +175,13 @@ func TestValidRevertedTransaction(t *testing.T) {
t.Fatal(err)
}
defer tpt.Close()
// Mine a few extra blocks on tpt to get past the signature hardfork height.
for i := 0; i < 10; i++ {
_, err = tpt.miner.AddBlock()
if err != nil {
t.Fatal(err)
}
}
tpt2, err := blankTpoolTester(t.Name() + "-tpt2")
if err != nil {
t.Fatal(err)
......
......@@ -16,6 +16,16 @@ func TestUpdate(t *testing.T) {
if err != nil {
t.Fatal(err)
}
// Mine a few more blocks to get past the hardfork height.
for i := types.BlockHeight(0); i <= 2; i++ {
b, _ := wt.miner.FindBlock()
err := wt.cs.AcceptBlock(b)
if err != nil {
t.Fatal(err)
}
}
// mine a block and add it to the consensus set
b, err := wt.miner.FindBlock()
if err != nil {
......
......@@ -4,6 +4,7 @@ import (
"io/ioutil"
"testing"
"time"
"unsafe"
"gitlab.com/NebulousLabs/Sia/crypto"
"gitlab.com/NebulousLabs/Sia/types"
......@@ -134,7 +135,7 @@ func TestMinerHeader(t *testing.T) {
copy(header[:], targetAndHeader[32:])
headerHash := crypto.HashObject(header)
for headerHash[0] >= types.RootTarget[0] {
header[35]++
*(*uint64)(unsafe.Pointer(&header[32])) += types.ASICHardforkFactor
headerHash = crypto.HashObject(header)
}
......
......@@ -40,7 +40,7 @@ func solveHeader(target types.Target, bh types.BlockHeader) (types.BlockHeader,
return bh, nil
}
*(*uint64)(unsafe.Pointer(&header[32])) = nonce
nonce++
nonce += types.ASICHardforkFactor
}
return bh, errors.New("couldn't solve block")
}
......@@ -15,6 +15,19 @@ import (
)
var (
// ASICHardforkHeight is the height at which the hardfork targeting
// selected ASICs was activated.
ASICHardforkHeight BlockHeight
// ASICHardforkFactor is the factor by which the hashrate of targeted
// ASICs will be reduced.
ASICHardforkFactor = uint64(1)
// ASICHardforkReplayProtectionPrefix is a byte that prefixes
// SiacoinInputs and SiafundInputs when calculating SigHashes to protect
// against replay attacks.
ASICHardforkReplayProtectionPrefix = []byte(nil)
// BlockFrequency is the desired number of seconds that
// should elapse, on average, between successive Blocks.
BlockFrequency BlockHeight
......@@ -149,6 +162,8 @@ func init() {
// can coordinate their actions over a the developer testnets, but fast
// enough that there isn't much time wasted on waiting for things to
// happen.
ASICHardforkHeight = 20
BlockFrequency = 12 // 12 seconds: slow enough for developers to see ~each block, fast enough that blocks don't waste time.
MaturityDelay = 10 // 60 seconds before a delayed output matures.
GenesisTimestamp = Timestamp(1424139000) // Change as necessary.
......@@ -187,6 +202,8 @@ func init() {
} else if build.Release == "testing" {
// 'testing' settings are for automatic testing, and create much faster
// environments than a human can interact with.
ASICHardforkHeight = 5
BlockFrequency = 1 // As fast as possible
MaturityDelay = 3
GenesisTimestamp = CurrentTimestamp() - 1e6
......@@ -231,6 +248,7 @@ func init() {
} else if build.Release == "standard" {
// 'standard' settings are for the full network. They are slow enough
// that the network is secure in a real-world byzantine environment.
ASICHardforkHeight = 179000
// A block time of 1 block per 10 minutes is chosen to follow Bitcoin's
// example. The security lost by lowering the block time is not
......
......@@ -196,6 +196,9 @@ func (t *Transaction) wholeSigHash(sig TransactionSignature, height BlockHeight)
e.WriteInt(len((t.SiacoinInputs)))
for i := range t.SiacoinInputs {
if height >= ASICHardforkHeight {
e.Write(ASICHardforkReplayProtectionPrefix)
}
t.SiacoinInputs[i].MarshalSia(e)
}
e.WriteInt(len((t.SiacoinOutputs)))
......@@ -216,6 +219,9 @@ func (t *Transaction) wholeSigHash(sig TransactionSignature, height BlockHeight)
}
e.WriteInt(len((t.SiafundInputs)))
for i := range t.SiafundInputs {
if height >= ASICHardforkHeight {
e.Write(ASICHardforkReplayProtectionPrefix)
}
t.SiafundInputs[i].MarshalSia(e)
}
e.WriteInt(len((t.SiafundOutputs)))
......@@ -249,6 +255,9 @@ func (t *Transaction) partialSigHash(cf CoveredFields, height BlockHeight) (hash
h := crypto.NewHash()
for _, input := range cf.SiacoinInputs {
if height >= ASICHardforkHeight {
h.Write(ASICHardforkReplayProtectionPrefix)
}
t.SiacoinInputs[input].MarshalSia(h)
}
for _, output := range cf.SiacoinOutputs {
......@@ -264,6 +273,9 @@ func (t *Transaction) partialSigHash(cf CoveredFields, height BlockHeight) (hash
t.StorageProofs[storageProof].MarshalSia(h)
}
for _, siafundInput := range cf.SiafundInputs {
if height >= ASICHardforkHeight {
h.Write(ASICHardforkReplayProtectionPrefix)
}
t.SiafundInputs[siafundInput].MarshalSia(h)
}
for _, siafundOutput := range cf.SiafundOutputs {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment