diff --git a/README.md b/README.md index f6c49cc2d..3553a5e35 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ Ethereum Ethereum Go Development package (C) Jeffrey Wilcke Ethereum is currently in its testing phase. The current state is "Proof -of Concept 2". For build instructions see the [Wiki](https://github.com/ethereum/go-ethereum/wiki/Building-Edge). +of Concept 3". For build instructions see the [Wiki](https://github.com/ethereum/go-ethereum/wiki/Building-Ethereum(Go)). Ethereum Go is split up in several sub packages Please refer to each individual package for more information. @@ -35,7 +35,7 @@ get a node and connectivity going. Build ======= -This is the Developer package. For the development client please see +This is the Developer package. For the Ethereal client please see [Ethereum(G)](https://github.com/ethereum/go-ethereum). `go get -u github.com/ethereum/eth-go` diff --git a/ethchain/dagger.go b/ethchain/dagger.go index c33b3c14e..4d2034e20 100644 --- a/ethchain/dagger.go +++ b/ethchain/dagger.go @@ -11,7 +11,7 @@ import ( ) type PoW interface { - Search(block *Block, breakChan chan bool) []byte + Search(block *Block, minerChan chan ethutil.React) []byte Verify(hash []byte, diff *big.Int, nonce []byte) bool } @@ -19,19 +19,32 @@ type EasyPow struct { hash *big.Int } -func (pow *EasyPow) Search(block *Block, breakChan chan bool) []byte { +func (pow *EasyPow) Search(block *Block, minerChan chan ethutil.React) []byte { r := rand.New(rand.NewSource(time.Now().UnixNano())) hash := block.HashNoNonce() diff := block.Difficulty + i := int64(0) + start := time.Now().UnixNano() for { select { - case shouldbreak := <-breakChan: - if shouldbreak { - log.Println("Got signal: Breaking out mining.") + case chanMessage := <-minerChan: + if _, ok := chanMessage.Resource.(*Block); ok { + log.Println("BREAKING OUT: BLOCK") + return nil + } + if _, ok := chanMessage.Resource.(*Transaction); ok { + log.Println("BREAKING OUT: TX") return nil } default: + i++ + if i%1234567 == 0 { + elapsed := time.Now().UnixNano() - start + hashes := ((float64(1e9) / float64(elapsed)) * float64(i)) / 1000 + log.Println("Hashing @", int64(hashes), "khash") + } + sha := ethutil.Sha3Bin(big.NewInt(r.Int63()).Bytes()) if pow.Verify(hash, diff, sha) { return sha diff --git a/ethchain/keypair.go b/ethchain/keypair.go new file mode 100644 index 000000000..9fdc95972 --- /dev/null +++ b/ethchain/keypair.go @@ -0,0 +1,74 @@ +package ethchain + +import ( + "github.com/ethereum/eth-go/ethutil" + "math/big" +) + +type KeyPair struct { + PrivateKey []byte + PublicKey []byte + + // The associated account + account *Account + state *State +} + +func NewKeyPairFromValue(val *ethutil.Value) *KeyPair { + keyPair := &KeyPair{PrivateKey: val.Get(0).Bytes(), PublicKey: val.Get(1).Bytes()} + + return keyPair +} + +func (k *KeyPair) Address() []byte { + return ethutil.Sha3Bin(k.PublicKey[1:])[12:] +} + +func (k *KeyPair) Account() *Account { + if k.account == nil { + k.account = k.state.GetAccount(k.Address()) + } + + return k.account +} + +// Create transaction, creates a new and signed transaction, ready for processing +func (k *KeyPair) CreateTx(receiver []byte, value *big.Int, data []string) *Transaction { + tx := NewTransaction(receiver, value, data) + tx.Nonce = k.account.Nonce + + // Sign the transaction with the private key in this key chain + tx.Sign(k.PrivateKey) + + return tx +} + +func (k *KeyPair) RlpEncode() []byte { + return ethutil.EmptyValue().Append(k.PrivateKey).Append(k.PublicKey).Encode() +} + +type KeyRing struct { + keys []*KeyPair +} + +func (k *KeyRing) Add(pair *KeyPair) { + k.keys = append(k.keys, pair) +} + +// The public "singleton" keyring +var keyRing *KeyRing + +func GetKeyRing(state *State) *KeyRing { + if keyRing == nil { + keyRing = &KeyRing{} + + data, _ := ethutil.Config.Db.Get([]byte("KeyRing")) + it := ethutil.NewValueFromBytes(data).NewIterator() + for it.Next() { + v := it.Value() + keyRing.Add(NewKeyPairFromValue(v)) + } + } + + return keyRing +} diff --git a/ethchain/state_manager.go b/ethchain/state_manager.go index 2652f3f29..39dece40e 100644 --- a/ethchain/state_manager.go +++ b/ethchain/state_manager.go @@ -22,7 +22,6 @@ type EthManager interface { Reactor() *ethutil.ReactorEngine } -// TODO rename to state manager type StateManager struct { // Mutex for locking the block processor. Blocks can only be handled one at a time mutex sync.Mutex diff --git a/ethereum.go b/ethereum.go index 302f3c04f..c906a6954 100644 --- a/ethereum.go +++ b/ethereum.go @@ -271,20 +271,45 @@ func (s *Ethereum) Start() { if ethutil.Config.Seed { ethutil.Config.Log.Debugln("Seeding") - // Testnet seed bootstrapping - resp, err := http.Get("https://www.ethereum.org/servers.poc3.txt") - if err != nil { - log.Println("Fetching seed failed:", err) - return - } - defer resp.Body.Close() - body, err := ioutil.ReadAll(resp.Body) - if err != nil { - log.Println("Reading seed failed:", err) - return - } + // DNS Bootstrapping + _, nodes, err := net.LookupSRV("eth", "tcp", "ethereum.org") + if err == nil { + peers := []string{} + // Iterate SRV nodes + for _, n := range nodes { + target := n.Target + port := strconv.Itoa(int(n.Port)) + // Resolve target to ip (Go returns list, so may resolve to multiple ips?) + addr, err := net.LookupHost(target) + if err == nil { + for _, a := range addr { + // Build string out of SRV port and Resolved IP + peer := net.JoinHostPort(a, port) + log.Println("Found DNS Bootstrap Peer:", peer) + peers = append(peers, peer) + } + } else { + log.Println("Couldn't resolve :", target) + } + } + // Connect to Peer list + s.ProcessPeerList(peers) + } else { + // Fallback to servers.poc3.txt + resp, err := http.Get("http://www.ethereum.org/servers.poc3.txt") + if err != nil { + log.Println("Fetching seed failed:", err) + return + } + defer resp.Body.Close() + body, err := ioutil.ReadAll(resp.Body) + if err != nil { + log.Println("Reading seed failed:", err) + return + } - s.ConnectToPeer(string(body)) + s.ConnectToPeer(string(body)) + } } } diff --git a/ethutil/trie.go b/ethutil/trie.go index a17dc37ad..c67f750bc 100644 --- a/ethutil/trie.go +++ b/ethutil/trie.go @@ -219,18 +219,6 @@ func (t *Trie) UpdateState(node interface{}, key []int, value string) interface{ } func (t *Trie) Put(node interface{}) interface{} { - /* - enc := Encode(node) - if len(enc) >= 32 { - var sha []byte - sha = Sha3Bin(enc) - //t.db.Put([]byte(sha), enc) - - return sha - } - return node - */ - /* TODO? c := Conv(t.Root)