diff options
Diffstat (limited to 'cmd')
-rw-r--r-- | cmd/evm/disasm.go | 5 | ||||
-rw-r--r-- | cmd/evm/main.go | 7 | ||||
-rw-r--r-- | cmd/evm/runner.go | 59 | ||||
-rw-r--r-- | cmd/faucet/faucet.go | 5 | ||||
-rw-r--r-- | cmd/geth/accountcmd_test.go | 12 | ||||
-rw-r--r-- | cmd/geth/main.go | 23 | ||||
-rw-r--r-- | cmd/geth/misccmd.go | 63 | ||||
-rw-r--r-- | cmd/geth/usage.go | 2 | ||||
-rw-r--r-- | cmd/puppeth/module_dashboard.go | 5 | ||||
-rw-r--r-- | cmd/puppeth/module_ethstats.go | 30 | ||||
-rw-r--r-- | cmd/puppeth/module_faucet.go | 5 | ||||
-rw-r--r-- | cmd/puppeth/module_nginx.go | 5 | ||||
-rw-r--r-- | cmd/puppeth/module_node.go | 5 | ||||
-rw-r--r-- | cmd/puppeth/ssh.go | 2 | ||||
-rw-r--r-- | cmd/puppeth/wizard.go | 58 | ||||
-rw-r--r-- | cmd/puppeth/wizard_ethstats.go | 18 | ||||
-rw-r--r-- | cmd/puppeth/wizard_network.go | 26 | ||||
-rw-r--r-- | cmd/swarm/cleandb.go | 38 | ||||
-rw-r--r-- | cmd/swarm/db.go | 116 | ||||
-rw-r--r-- | cmd/swarm/main.go | 61 | ||||
-rw-r--r-- | cmd/swarm/run_test.go | 1 | ||||
-rw-r--r-- | cmd/swarm/upload_test.go | 2 | ||||
-rw-r--r-- | cmd/utils/flags.go | 21 |
23 files changed, 414 insertions, 155 deletions
diff --git a/cmd/evm/disasm.go b/cmd/evm/disasm.go index a78b2a8e1..4a442cf78 100644 --- a/cmd/evm/disasm.go +++ b/cmd/evm/disasm.go @@ -46,8 +46,5 @@ func disasmCmd(ctx *cli.Context) error { code := strings.TrimSpace(string(in[:])) fmt.Printf("%v\n", code) - if err = asm.PrintDisassembled(code); err != nil { - return err - } - return nil + return asm.PrintDisassembled(code) } diff --git a/cmd/evm/main.go b/cmd/evm/main.go index 1892ae3d3..a2e3b048e 100644 --- a/cmd/evm/main.go +++ b/cmd/evm/main.go @@ -53,7 +53,7 @@ var ( } CodeFileFlag = cli.StringFlag{ Name: "codefile", - Usage: "file containing EVM code", + Usage: "File containing EVM code. If '-' is specified, code is read from stdin ", } GasFlag = cli.Uint64Flag{ Name: "gas", @@ -102,6 +102,10 @@ var ( Name: "sender", Usage: "The transaction origin", } + ReceiverFlag = cli.StringFlag{ + Name: "receiver", + Usage: "The transaction receiver (execution context)", + } DisableMemoryFlag = cli.BoolFlag{ Name: "nomemory", Usage: "disable memory output", @@ -131,6 +135,7 @@ func init() { GenesisFlag, MachineFlag, SenderFlag, + ReceiverFlag, DisableMemoryFlag, DisableStackFlag, } diff --git a/cmd/evm/runner.go b/cmd/evm/runner.go index 3f95a0c93..ae5678110 100644 --- a/cmd/evm/runner.go +++ b/cmd/evm/runner.go @@ -84,6 +84,7 @@ func runCmd(ctx *cli.Context) error { statedb *state.StateDB chainConfig *params.ChainConfig sender = common.StringToAddress("sender") + receiver = common.StringToAddress("receiver") ) if ctx.GlobalBool(MachineFlag.Name) { tracer = NewJSONLogger(logconfig, os.Stdout) @@ -104,46 +105,52 @@ func runCmd(ctx *cli.Context) error { if ctx.GlobalString(SenderFlag.Name) != "" { sender = common.HexToAddress(ctx.GlobalString(SenderFlag.Name)) } - statedb.CreateAccount(sender) + if ctx.GlobalString(ReceiverFlag.Name) != "" { + receiver = common.HexToAddress(ctx.GlobalString(ReceiverFlag.Name)) + } + var ( code []byte ret []byte err error ) - if fn := ctx.Args().First(); len(fn) > 0 { + // The '--code' or '--codefile' flag overrides code in state + if ctx.GlobalString(CodeFileFlag.Name) != "" { + var hexcode []byte + var err error + // If - is specified, it means that code comes from stdin + if ctx.GlobalString(CodeFileFlag.Name) == "-" { + //Try reading from stdin + if hexcode, err = ioutil.ReadAll(os.Stdin); err != nil { + fmt.Printf("Could not load code from stdin: %v\n", err) + os.Exit(1) + } + } else { + // Codefile with hex assembly + if hexcode, err = ioutil.ReadFile(ctx.GlobalString(CodeFileFlag.Name)); err != nil { + fmt.Printf("Could not load code from file: %v\n", err) + os.Exit(1) + } + } + code = common.Hex2Bytes(string(bytes.TrimRight(hexcode, "\n"))) + + } else if ctx.GlobalString(CodeFlag.Name) != "" { + code = common.Hex2Bytes(ctx.GlobalString(CodeFlag.Name)) + } else if fn := ctx.Args().First(); len(fn) > 0 { + // EASM-file to compile src, err := ioutil.ReadFile(fn) if err != nil { return err } - bin, err := compiler.Compile(fn, src, false) if err != nil { return err } code = common.Hex2Bytes(bin) - } else if ctx.GlobalString(CodeFlag.Name) != "" { - code = common.Hex2Bytes(ctx.GlobalString(CodeFlag.Name)) - } else { - var hexcode []byte - if ctx.GlobalString(CodeFileFlag.Name) != "" { - var err error - hexcode, err = ioutil.ReadFile(ctx.GlobalString(CodeFileFlag.Name)) - if err != nil { - fmt.Printf("Could not load code from file: %v\n", err) - os.Exit(1) - } - } else { - var err error - hexcode, err = ioutil.ReadAll(os.Stdin) - if err != nil { - fmt.Printf("Could not load code from stdin: %v\n", err) - os.Exit(1) - } - } - code = common.Hex2Bytes(string(bytes.TrimRight(hexcode, "\n"))) } + initialGas := ctx.GlobalUint64(GasFlag.Name) runtimeConfig := runtime.Config{ Origin: sender, @@ -180,9 +187,9 @@ func runCmd(ctx *cli.Context) error { input := append(code, common.Hex2Bytes(ctx.GlobalString(InputFlag.Name))...) ret, _, leftOverGas, err = runtime.Create(input, &runtimeConfig) } else { - receiver := common.StringToAddress("receiver") - statedb.SetCode(receiver, code) - + if len(code) > 0 { + statedb.SetCode(receiver, code) + } ret, leftOverGas, err = runtime.Call(receiver, common.Hex2Bytes(ctx.GlobalString(InputFlag.Name)), &runtimeConfig) } execTime := time.Since(tstart) diff --git a/cmd/faucet/faucet.go b/cmd/faucet/faucet.go index c06c4365b..8cd62441e 100644 --- a/cmd/faucet/faucet.go +++ b/cmd/faucet/faucet.go @@ -413,8 +413,9 @@ func (f *faucet) apiHandler(conn *websocket.Conn) { // Iterate over all the files and look for Ethereum addresses var address common.Address for _, file := range gist.Files { - if len(file.Content) == 2+common.AddressLength*2 { - address = common.HexToAddress(file.Content) + content := strings.TrimSpace(file.Content) + if len(content) == 2+common.AddressLength*2 { + address = common.HexToAddress(content) } } if address == (common.Address{}) { diff --git a/cmd/geth/accountcmd_test.go b/cmd/geth/accountcmd_test.go index e146323ee..66e3e02a4 100644 --- a/cmd/geth/accountcmd_test.go +++ b/cmd/geth/accountcmd_test.go @@ -146,7 +146,7 @@ Passphrase: {{.InputLine "foobar"}} wantMessages := []string{ "Unlocked account", - "=0xf466859ead1932d743d622cb74fc058882e8648a", + "=0xf466859eAD1932D743d622CB74FC058882E8648A", } for _, m := range wantMessages { if !strings.Contains(geth.StderrText(), m) { @@ -191,8 +191,8 @@ Passphrase: {{.InputLine "foobar"}} wantMessages := []string{ "Unlocked account", - "=0x7ef5a6135f1fd6a02593eedc869c6d41d934aef8", - "=0x289d485d9771714cce91d3393d764e1311907acc", + "=0x7EF5A6135f1FD6a02593eEdC869c6D41D934aef8", + "=0x289d485D9771714CCe91D3393D764E1311907ACc", } for _, m := range wantMessages { if !strings.Contains(geth.StderrText(), m) { @@ -211,8 +211,8 @@ func TestUnlockFlagPasswordFile(t *testing.T) { wantMessages := []string{ "Unlocked account", - "=0x7ef5a6135f1fd6a02593eedc869c6d41d934aef8", - "=0x289d485d9771714cce91d3393d764e1311907acc", + "=0x7EF5A6135f1FD6a02593eEdC869c6D41D934aef8", + "=0x289d485D9771714CCe91D3393D764E1311907ACc", } for _, m := range wantMessages { if !strings.Contains(geth.StderrText(), m) { @@ -261,7 +261,7 @@ In order to avoid this warning, you need to remove the following duplicate key f wantMessages := []string{ "Unlocked account", - "=0xf466859ead1932d743d622cb74fc058882e8648a", + "=0xf466859eAD1932D743d622CB74FC058882E8648A", } for _, m := range wantMessages { if !strings.Contains(geth.StderrText(), m) { diff --git a/cmd/geth/main.go b/cmd/geth/main.go index 607414bbb..8166c9ce8 100644 --- a/cmd/geth/main.go +++ b/cmd/geth/main.go @@ -21,6 +21,7 @@ import ( "fmt" "os" "runtime" + "sort" "strings" "time" @@ -67,6 +68,8 @@ var ( utils.EthashDatasetsInMemoryFlag, utils.EthashDatasetsOnDiskFlag, utils.TxPoolNoLocalsFlag, + utils.TxPoolJournalFlag, + utils.TxPoolRejournalFlag, utils.TxPoolPriceLimitFlag, utils.TxPoolPriceBumpFlag, utils.TxPoolAccountSlotsFlag, @@ -155,6 +158,7 @@ func init() { attachCommand, javascriptCommand, // See misccmd.go: + makecacheCommand, makedagCommand, versionCommand, bugCommand, @@ -162,6 +166,7 @@ func init() { // See config.go dumpConfigCommand, } + sort.Sort(cli.CommandsByName(app.Commands)) app.Flags = append(app.Flags, nodeFlags...) app.Flags = append(app.Flags, rpcFlags...) @@ -234,24 +239,30 @@ func startNode(ctx *cli.Context, stack *node.Node) { } stateReader := ethclient.NewClient(rpcClient) - // Open and self derive any wallets already attached + // Open any wallets already attached for _, wallet := range stack.AccountManager().Wallets() { if err := wallet.Open(""); err != nil { log.Warn("Failed to open wallet", "url", wallet.URL(), "err", err) - } else { - wallet.SelfDerive(accounts.DefaultBaseDerivationPath, stateReader) } } // Listen for wallet event till termination for event := range events { - if event.Arrive { + switch event.Kind { + case accounts.WalletArrived: if err := event.Wallet.Open(""); err != nil { log.Warn("New wallet appeared, failed to open", "url", event.Wallet.URL(), "err", err) + } + case accounts.WalletOpened: + status, _ := event.Wallet.Status() + log.Info("New wallet appeared", "url", event.Wallet.URL(), "status", status) + + if event.Wallet.URL().Scheme == "ledger" { + event.Wallet.SelfDerive(accounts.DefaultLedgerBaseDerivationPath, stateReader) } else { - log.Info("New wallet appeared", "url", event.Wallet.URL(), "status", event.Wallet.Status()) event.Wallet.SelfDerive(accounts.DefaultBaseDerivationPath, stateReader) } - } else { + + case accounts.WalletDropped: log.Info("Old wallet dropped", "url", event.Wallet.URL()) event.Wallet.Close() } diff --git a/cmd/geth/misccmd.go b/cmd/geth/misccmd.go index 62b93d65a..2e68dcda3 100644 --- a/cmd/geth/misccmd.go +++ b/cmd/geth/misccmd.go @@ -18,9 +18,7 @@ package main import ( "fmt" - "io/ioutil" "os" - "path/filepath" "runtime" "strconv" "strings" @@ -33,14 +31,27 @@ import ( ) var ( + makecacheCommand = cli.Command{ + Action: utils.MigrateFlags(makecache), + Name: "makecache", + Usage: "Generate ethash verification cache (for testing)", + ArgsUsage: "<blockNum> <outputDir>", + Category: "MISCELLANEOUS COMMANDS", + Description: ` +The makecache command generates an ethash cache in <outputDir>. + +This command exists to support the system testing project. +Regular users do not need to execute it. +`, + } makedagCommand = cli.Command{ Action: utils.MigrateFlags(makedag), Name: "makedag", - Usage: "Generate ethash DAG (for testing)", + Usage: "Generate ethash mining DAG (for testing)", ArgsUsage: "<blockNum> <outputDir>", Category: "MISCELLANEOUS COMMANDS", Description: ` -The makedag command generates an ethash DAG in /tmp/dag. +The makedag command generates an ethash DAG in <outputDir>. This command exists to support the system testing project. Regular users do not need to execute it. @@ -65,33 +76,33 @@ The output of this command is supposed to be machine-readable. } ) +// makecache generates an ethash verification cache into the provided folder. +func makecache(ctx *cli.Context) error { + args := ctx.Args() + if len(args) != 2 { + utils.Fatalf(`Usage: geth makecache <block number> <outputdir>`) + } + block, err := strconv.ParseUint(args[0], 0, 64) + if err != nil { + utils.Fatalf("Invalid block number: %v", err) + } + ethash.MakeCache(block, args[1]) + + return nil +} + +// makedag generates an ethash mining DAG into the provided folder. func makedag(ctx *cli.Context) error { args := ctx.Args() - wrongArgs := func() { + if len(args) != 2 { utils.Fatalf(`Usage: geth makedag <block number> <outputdir>`) } - switch { - case len(args) == 2: - blockNum, err := strconv.ParseUint(args[0], 0, 64) - dir := args[1] - if err != nil { - wrongArgs() - } else { - dir = filepath.Clean(dir) - // seems to require a trailing slash - if !strings.HasSuffix(dir, "/") { - dir = dir + "/" - } - _, err = ioutil.ReadDir(dir) - if err != nil { - utils.Fatalf("Can't find dir") - } - fmt.Println("making DAG, this could take awhile...") - ethash.MakeDataset(blockNum, dir) - } - default: - wrongArgs() + block, err := strconv.ParseUint(args[0], 0, 64) + if err != nil { + utils.Fatalf("Invalid block number: %v", err) } + ethash.MakeDataset(block, args[1]) + return nil } diff --git a/cmd/geth/usage.go b/cmd/geth/usage.go index 275aad674..80861d852 100644 --- a/cmd/geth/usage.go +++ b/cmd/geth/usage.go @@ -96,6 +96,8 @@ var AppHelpFlagGroups = []flagGroup{ Name: "TRANSACTION POOL", Flags: []cli.Flag{ utils.TxPoolNoLocalsFlag, + utils.TxPoolJournalFlag, + utils.TxPoolRejournalFlag, utils.TxPoolPriceLimitFlag, utils.TxPoolPriceBumpFlag, utils.TxPoolAccountSlotsFlag, diff --git a/cmd/puppeth/module_dashboard.go b/cmd/puppeth/module_dashboard.go index 17f119111..1cf6cab79 100644 --- a/cmd/puppeth/module_dashboard.go +++ b/cmd/puppeth/module_dashboard.go @@ -425,6 +425,11 @@ services: - "{{.Port}}:80"{{else}} environment: - VIRTUAL_HOST={{.VHost}}{{end}} + logging: + driver: "json-file" + options: + max-size: "1m" + max-file: "10" restart: always ` diff --git a/cmd/puppeth/module_ethstats.go b/cmd/puppeth/module_ethstats.go index 571df1454..5d3fa5fc0 100644 --- a/cmd/puppeth/module_ethstats.go +++ b/cmd/puppeth/module_ethstats.go @@ -42,7 +42,7 @@ RUN \ WORKDIR /eth-netstats EXPOSE 3000 -RUN echo 'module.exports = {trusted: [{{.Trusted}}], banned: []};' > lib/utils/config.js +RUN echo 'module.exports = {trusted: [{{.Trusted}}], banned: [{{.Banned}}]};' > lib/utils/config.js CMD ["npm", "start"] ` @@ -59,25 +59,37 @@ services: - "{{.Port}}:3000"{{end}} environment: - WS_SECRET={{.Secret}}{{if .VHost}} - - VIRTUAL_HOST={{.VHost}}{{end}} + - VIRTUAL_HOST={{.VHost}}{{end}}{{if .Banned}} + - BANNED={{.Banned}}{{end}} + logging: + driver: "json-file" + options: + max-size: "1m" + max-file: "10" restart: always ` // deployEthstats deploys a new ethstats container to a remote machine via SSH, // docker and docker-compose. If an instance with the specified network name // already exists there, it will be overwritten! -func deployEthstats(client *sshClient, network string, port int, secret string, vhost string, trusted []string) ([]byte, error) { +func deployEthstats(client *sshClient, network string, port int, secret string, vhost string, trusted []string, banned []string) ([]byte, error) { // Generate the content to upload to the server workdir := fmt.Sprintf("%d", rand.Int63()) files := make(map[string][]byte) + trustedLabels := make([]string, len(trusted)) for i, address := range trusted { - trusted[i] = fmt.Sprintf("\"%s\"", address) + trustedLabels[i] = fmt.Sprintf("\"%s\"", address) + } + bannedLabels := make([]string, len(banned)) + for i, address := range banned { + bannedLabels[i] = fmt.Sprintf("\"%s\"", address) } dockerfile := new(bytes.Buffer) template.Must(template.New("").Parse(ethstatsDockerfile)).Execute(dockerfile, map[string]interface{}{ - "Trusted": strings.Join(trusted, ", "), + "Trusted": strings.Join(trustedLabels, ", "), + "Banned": strings.Join(bannedLabels, ", "), }) files[filepath.Join(workdir, "Dockerfile")] = dockerfile.Bytes() @@ -87,6 +99,7 @@ func deployEthstats(client *sshClient, network string, port int, secret string, "Port": port, "Secret": secret, "VHost": vhost, + "Banned": strings.Join(banned, ","), }) files[filepath.Join(workdir, "docker-compose.yaml")] = composefile.Bytes() @@ -107,11 +120,12 @@ type ethstatsInfos struct { port int secret string config string + banned []string } // String implements the stringer interface. func (info *ethstatsInfos) String() string { - return fmt.Sprintf("host=%s, port=%d, secret=%s", info.host, info.port, info.secret) + return fmt.Sprintf("host=%s, port=%d, secret=%s, banned=%v", info.host, info.port, info.secret, info.banned) } // checkEthstats does a health-check against an ethstats server to verify whether @@ -145,6 +159,9 @@ func checkEthstats(client *sshClient, network string) (*ethstatsInfos, error) { if port != 80 && port != 443 { config += fmt.Sprintf(":%d", port) } + // Retrieve the IP blacklist + banned := strings.Split(infos.envvars["BANNED"], ",") + // Run a sanity check to see if the port is reachable if err = checkPort(host, port); err != nil { log.Warn("Ethstats service seems unreachable", "server", host, "port", port, "err", err) @@ -155,5 +172,6 @@ func checkEthstats(client *sshClient, network string) (*ethstatsInfos, error) { port: port, secret: secret, config: config, + banned: banned, }, nil } diff --git a/cmd/puppeth/module_faucet.go b/cmd/puppeth/module_faucet.go index 5a5dc6506..acf1e4324 100644 --- a/cmd/puppeth/module_faucet.go +++ b/cmd/puppeth/module_faucet.go @@ -82,6 +82,11 @@ services: - CAPTCHA_SECRET={{.CaptchaSecret}}{{if .VHost}} - VIRTUAL_HOST={{.VHost}} - VIRTUAL_PORT=8080{{end}} + logging: + driver: "json-file" + options: + max-size: "1m" + max-file: "10" restart: always ` diff --git a/cmd/puppeth/module_nginx.go b/cmd/puppeth/module_nginx.go index 0eac5ace5..fd6d1d74e 100644 --- a/cmd/puppeth/module_nginx.go +++ b/cmd/puppeth/module_nginx.go @@ -43,6 +43,11 @@ services: - "{{.Port}}:80" volumes: - /var/run/docker.sock:/tmp/docker.sock:ro + logging: + driver: "json-file" + options: + max-size: "1m" + max-file: "10" restart: always ` diff --git a/cmd/puppeth/module_node.go b/cmd/puppeth/module_node.go index ce1d34135..9fe97c892 100644 --- a/cmd/puppeth/module_node.go +++ b/cmd/puppeth/module_node.go @@ -68,6 +68,11 @@ services: - MINER_NAME={{.Etherbase}} - GAS_TARGET={{.GasTarget}} - GAS_PRICE={{.GasPrice}} + logging: + driver: "json-file" + options: + max-size: "1m" + max-file: "10" restart: always ` diff --git a/cmd/puppeth/ssh.go b/cmd/puppeth/ssh.go index 93668945c..26f846685 100644 --- a/cmd/puppeth/ssh.go +++ b/cmd/puppeth/ssh.go @@ -122,7 +122,7 @@ func dial(server string, pubkey []byte) (*sshClient, error) { } } // If a public key exists for this SSH server, check that it matches - if bytes.Compare(pubkey, key.Marshal()) == 0 { + if bytes.Equal(pubkey, key.Marshal()) { return nil } // We have a mismatch, forbid connecting diff --git a/cmd/puppeth/wizard.go b/cmd/puppeth/wizard.go index 51e64688e..518741279 100644 --- a/cmd/puppeth/wizard.go +++ b/cmd/puppeth/wizard.go @@ -22,6 +22,7 @@ import ( "fmt" "io/ioutil" "math/big" + "net" "os" "path/filepath" "sort" @@ -106,17 +107,15 @@ func (w *wizard) readString() string { // readDefaultString reads a single line from stdin, trimming if from spaces. If // an empty line is entered, the default value is returned. func (w *wizard) readDefaultString(def string) string { - for { - fmt.Printf("> ") - text, err := w.in.ReadString('\n') - if err != nil { - log.Crit("Failed to read user input", "err", err) - } - if text = strings.TrimSpace(text); text != "" { - return text - } - return def + fmt.Printf("> ") + text, err := w.in.ReadString('\n') + if err != nil { + log.Crit("Failed to read user input", "err", err) + } + if text = strings.TrimSpace(text); text != "" { + return text } + return def } // readInt reads a single line from stdin, trimming if from spaces, enforcing it @@ -162,6 +161,7 @@ func (w *wizard) readDefaultInt(def int) int { } } +/* // readFloat reads a single line from stdin, trimming if from spaces, enforcing it // to parse into a float. func (w *wizard) readFloat() float64 { @@ -182,6 +182,7 @@ func (w *wizard) readFloat() float64 { return val } } +*/ // readDefaultFloat reads a single line from stdin, trimming if from spaces, enforcing // it to parse into a float. If an empty line is entered, the default value is returned. @@ -207,15 +208,13 @@ func (w *wizard) readDefaultFloat(def float64) float64 { // readPassword reads a single line from stdin, trimming it from the trailing new // line and returns it. The input will not be echoed. func (w *wizard) readPassword() string { - for { - fmt.Printf("> ") - text, err := terminal.ReadPassword(int(syscall.Stdin)) - if err != nil { - log.Crit("Failed to read password", "err", err) - } - fmt.Println() - return string(text) + fmt.Printf("> ") + text, err := terminal.ReadPassword(int(syscall.Stdin)) + if err != nil { + log.Crit("Failed to read password", "err", err) } + fmt.Println() + return string(text) } // readAddress reads a single line from stdin, trimming if from spaces and converts @@ -279,3 +278,26 @@ func (w *wizard) readJSON() string { return string(blob) } } + +// readIPAddress reads a single line from stdin, trimming if from spaces and +// converts it to a network IP address. +func (w *wizard) readIPAddress() net.IP { + for { + // Read the IP address from the user + fmt.Printf("> ") + text, err := w.in.ReadString('\n') + if err != nil { + log.Crit("Failed to read user input", "err", err) + } + if text = strings.TrimSpace(text); text == "" { + return nil + } + // Make sure it looks ok and return it if so + ip := net.ParseIP(text) + if ip == nil { + log.Error("Invalid IP address, please retry") + continue + } + return ip + } +} diff --git a/cmd/puppeth/wizard_ethstats.go b/cmd/puppeth/wizard_ethstats.go index c117a6027..504d8fd9c 100644 --- a/cmd/puppeth/wizard_ethstats.go +++ b/cmd/puppeth/wizard_ethstats.go @@ -60,6 +60,22 @@ func (w *wizard) deployEthstats() { fmt.Printf("What should be the secret password for the API? (default = %s)\n", infos.secret) infos.secret = w.readDefaultString(infos.secret) } + // Gather any blacklists to ban from reporting + fmt.Println() + fmt.Printf("Keep existing IP %v blacklist (y/n)? (default = yes)\n", infos.banned) + if w.readDefaultString("y") != "y" { + infos.banned = nil + + fmt.Println() + fmt.Println("Which IP addresses should be blacklisted?") + for { + if ip := w.readIPAddress(); ip != nil { + infos.banned = append(infos.banned, ip.String()) + continue + } + break + } + } // Try to deploy the ethstats server on the host trusted := make([]string, 0, len(w.servers)) for _, client := range w.servers { @@ -67,7 +83,7 @@ func (w *wizard) deployEthstats() { trusted = append(trusted, client.address) } } - if out, err := deployEthstats(client, w.network, infos.port, infos.secret, infos.host, trusted); err != nil { + if out, err := deployEthstats(client, w.network, infos.port, infos.secret, infos.host, trusted, infos.banned); err != nil { log.Error("Failed to deploy ethstats container", "err", err) if len(out) > 0 { fmt.Printf("%s\n", out) diff --git a/cmd/puppeth/wizard_network.go b/cmd/puppeth/wizard_network.go index 0455e1ef3..ff2ff74f5 100644 --- a/cmd/puppeth/wizard_network.go +++ b/cmd/puppeth/wizard_network.go @@ -71,22 +71,20 @@ func (w *wizard) makeServer() string { fmt.Println() fmt.Println("Please enter remote server's address:") - for { - // Read and fial the server to ensure docker is present - input := w.readString() - - client, err := dial(input, nil) - if err != nil { - log.Error("Server not ready for puppeth", "err", err) - return "" - } - // All checks passed, start tracking the server - w.servers[input] = client - w.conf.Servers[input] = client.pubkey - w.conf.flush() + // Read and fial the server to ensure docker is present + input := w.readString() - return input + client, err := dial(input, nil) + if err != nil { + log.Error("Server not ready for puppeth", "err", err) + return "" } + // All checks passed, start tracking the server + w.servers[input] = client + w.conf.Servers[input] = client.pubkey + w.conf.flush() + + return input } // selectServer lists the user all the currnetly known servers to choose from, diff --git a/cmd/swarm/cleandb.go b/cmd/swarm/cleandb.go deleted file mode 100644 index 268076062..000000000 --- a/cmd/swarm/cleandb.go +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright 2017 The go-ethereum Authors -// This file is part of go-ethereum. -// -// go-ethereum is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// go-ethereum is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with go-ethereum. If not, see <http://www.gnu.org/licenses/>. - -package main - -import ( - "github.com/ethereum/go-ethereum/cmd/utils" - "github.com/ethereum/go-ethereum/swarm/storage" - "gopkg.in/urfave/cli.v1" -) - -func cleandb(ctx *cli.Context) { - args := ctx.Args() - if len(args) != 1 { - utils.Fatalf("Need path to chunks database as the first and only argument") - } - - chunkDbPath := args[0] - hash := storage.MakeHashFunc("SHA3") - dbStore, err := storage.NewDbStore(chunkDbPath, hash, 10000000, 0) - if err != nil { - utils.Fatalf("Cannot initialise dbstore: %v", err) - } - dbStore.Cleanup() -} diff --git a/cmd/swarm/db.go b/cmd/swarm/db.go new file mode 100644 index 000000000..dfd2d069b --- /dev/null +++ b/cmd/swarm/db.go @@ -0,0 +1,116 @@ +// Copyright 2017 The go-ethereum Authors +// This file is part of go-ethereum. +// +// go-ethereum is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// go-ethereum is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with go-ethereum. If not, see <http://www.gnu.org/licenses/>. + +package main + +import ( + "fmt" + "io" + "os" + "path/filepath" + + "github.com/ethereum/go-ethereum/cmd/utils" + "github.com/ethereum/go-ethereum/log" + "github.com/ethereum/go-ethereum/swarm/storage" + "gopkg.in/urfave/cli.v1" +) + +func dbExport(ctx *cli.Context) { + args := ctx.Args() + if len(args) != 2 { + utils.Fatalf("invalid arguments, please specify both <chunkdb> (path to a local chunk database) and <file> (path to write the tar archive to, - for stdout)") + } + + store, err := openDbStore(args[0]) + if err != nil { + utils.Fatalf("error opening local chunk database: %s", err) + } + defer store.Close() + + var out io.Writer + if args[1] == "-" { + out = os.Stdout + } else { + f, err := os.Create(args[1]) + if err != nil { + utils.Fatalf("error opening output file: %s", err) + } + defer f.Close() + out = f + } + + count, err := store.Export(out) + if err != nil { + utils.Fatalf("error exporting local chunk database: %s", err) + } + + log.Info(fmt.Sprintf("successfully exported %d chunks", count)) +} + +func dbImport(ctx *cli.Context) { + args := ctx.Args() + if len(args) != 2 { + utils.Fatalf("invalid arguments, please specify both <chunkdb> (path to a local chunk database) and <file> (path to read the tar archive from, - for stdin)") + } + + store, err := openDbStore(args[0]) + if err != nil { + utils.Fatalf("error opening local chunk database: %s", err) + } + defer store.Close() + + var in io.Reader + if args[1] == "-" { + in = os.Stdin + } else { + f, err := os.Open(args[1]) + if err != nil { + utils.Fatalf("error opening input file: %s", err) + } + defer f.Close() + in = f + } + + count, err := store.Import(in) + if err != nil { + utils.Fatalf("error importing local chunk database: %s", err) + } + + log.Info(fmt.Sprintf("successfully imported %d chunks", count)) +} + +func dbClean(ctx *cli.Context) { + args := ctx.Args() + if len(args) != 1 { + utils.Fatalf("invalid arguments, please specify <chunkdb> (path to a local chunk database)") + } + + store, err := openDbStore(args[0]) + if err != nil { + utils.Fatalf("error opening local chunk database: %s", err) + } + defer store.Close() + + store.Cleanup() +} + +func openDbStore(path string) (*storage.DbStore, error) { + if _, err := os.Stat(filepath.Join(path, "CURRENT")); err != nil { + return nil, fmt.Errorf("invalid chunkdb path: %s", err) + } + hash := storage.MakeHashFunc("SHA3") + return storage.NewDbStore(path, hash, 10000000, 0) +} diff --git a/cmd/swarm/main.go b/cmd/swarm/main.go index 4ae06a1c9..603fd9b94 100644 --- a/cmd/swarm/main.go +++ b/cmd/swarm/main.go @@ -25,6 +25,7 @@ import ( "os" "os/signal" "runtime" + "sort" "strconv" "strings" "syscall" @@ -240,15 +241,69 @@ Removes a path from the manifest }, }, { - Action: cleandb, + Name: "db", + Usage: "manage the local chunk database", + ArgsUsage: "db COMMAND", + Description: ` +Manage the local chunk database. +`, + Subcommands: []cli.Command{ + { + Action: dbExport, + Name: "export", + Usage: "export a local chunk database as a tar archive (use - to send to stdout)", + ArgsUsage: "<chunkdb> <file>", + Description: ` +Export a local chunk database as a tar archive (use - to send to stdout). + + swarm db export ~/.ethereum/swarm/bzz-KEY/chunks chunks.tar + +The export may be quite large, consider piping the output through the Unix +pv(1) tool to get a progress bar: + + swarm db export ~/.ethereum/swarm/bzz-KEY/chunks - | pv > chunks.tar +`, + }, + { + Action: dbImport, + Name: "import", + Usage: "import chunks from a tar archive into a local chunk database (use - to read from stdin)", + ArgsUsage: "<chunkdb> <file>", + Description: ` +Import chunks from a tar archive into a local chunk database (use - to read from stdin). + + swarm db import ~/.ethereum/swarm/bzz-KEY/chunks chunks.tar + +The import may be quite large, consider piping the input through the Unix +pv(1) tool to get a progress bar: + + pv chunks.tar | swarm db import ~/.ethereum/swarm/bzz-KEY/chunks - +`, + }, + { + Action: dbClean, + Name: "clean", + Usage: "remove corrupt entries from a local chunk database", + ArgsUsage: "<chunkdb>", + Description: ` +Remove corrupt entries from a local chunk database. +`, + }, + }, + }, + { + Action: func(ctx *cli.Context) { + utils.Fatalf("ERROR: 'swarm cleandb' has been removed, please use 'swarm db clean'.") + }, Name: "cleandb", - Usage: "Cleans database of corrupted entries", + Usage: "DEPRECATED: use 'swarm db clean'", ArgsUsage: " ", Description: ` -Cleans database of corrupted entries. +DEPRECATED: use 'swarm db clean'. `, }, } + sort.Sort(cli.CommandsByName(app.Commands)) app.Flags = []cli.Flag{ utils.IdentityFlag, diff --git a/cmd/swarm/run_test.go b/cmd/swarm/run_test.go index 05cbb27f1..aaaf9e1e5 100644 --- a/cmd/swarm/run_test.go +++ b/cmd/swarm/run_test.go @@ -161,6 +161,7 @@ func newTestNode(t *testing.T, dir string) *testNode { conf := &node.Config{ DataDir: dir, IPCPath: "bzzd.ipc", + NoUSB: true, } n, err := node.New(conf) if err != nil { diff --git a/cmd/swarm/upload_test.go b/cmd/swarm/upload_test.go index 5b74dd4f1..5656186e1 100644 --- a/cmd/swarm/upload_test.go +++ b/cmd/swarm/upload_test.go @@ -27,8 +27,6 @@ import ( // TestCLISwarmUp tests that running 'swarm up' makes the resulting file // available from all nodes via the HTTP API func TestCLISwarmUp(t *testing.T) { - t.Skip("flaky test") - // start 3 node cluster t.Log("starting 3 node cluster") cluster := newTestCluster(t, 3) diff --git a/cmd/utils/flags.go b/cmd/utils/flags.go index 0159364af..04728b5c6 100644 --- a/cmd/utils/flags.go +++ b/cmd/utils/flags.go @@ -213,6 +213,16 @@ var ( Name: "txpool.nolocals", Usage: "Disables price exemptions for locally submitted transactions", } + TxPoolJournalFlag = cli.StringFlag{ + Name: "txpool.journal", + Usage: "Disk journal for local transaction to survive node restarts", + Value: core.DefaultTxPoolConfig.Journal, + } + TxPoolRejournalFlag = cli.DurationFlag{ + Name: "txpool.rejournal", + Usage: "Time interval to regenerate the local transaction journal", + Value: core.DefaultTxPoolConfig.Rejournal, + } TxPoolPriceLimitFlag = cli.Uint64Flag{ Name: "txpool.pricelimit", Usage: "Minimum gas price limit to enforce for acceptance into the pool", @@ -838,6 +848,12 @@ func setTxPool(ctx *cli.Context, cfg *core.TxPoolConfig) { if ctx.GlobalIsSet(TxPoolNoLocalsFlag.Name) { cfg.NoLocals = ctx.GlobalBool(TxPoolNoLocalsFlag.Name) } + if ctx.GlobalIsSet(TxPoolJournalFlag.Name) { + cfg.Journal = ctx.GlobalString(TxPoolJournalFlag.Name) + } + if ctx.GlobalIsSet(TxPoolRejournalFlag.Name) { + cfg.Rejournal = ctx.GlobalDuration(TxPoolRejournalFlag.Name) + } if ctx.GlobalIsSet(TxPoolPriceLimitFlag.Name) { cfg.PriceLimit = ctx.GlobalUint64(TxPoolPriceLimitFlag.Name) } @@ -1077,7 +1093,10 @@ func MakeChain(ctx *cli.Context, stack *node.Node) (chain *core.BlockChain, chai engine := ethash.NewFaker() if !ctx.GlobalBool(FakePoWFlag.Name) { - engine = ethash.New("", 1, 0, "", 1, 0) + engine = ethash.New( + stack.ResolvePath(eth.DefaultConfig.EthashCacheDir), eth.DefaultConfig.EthashCachesInMem, eth.DefaultConfig.EthashCachesOnDisk, + stack.ResolvePath(eth.DefaultConfig.EthashDatasetDir), eth.DefaultConfig.EthashDatasetsInMem, eth.DefaultConfig.EthashDatasetsOnDisk, + ) } config, _, err := core.SetupGenesisBlock(chainDb, MakeGenesis(ctx)) if err != nil { |