Mining plays a crucial role in blockchain networks like Ethereum, especially in proof-of-work (PoW) consensus mechanisms. While Ethereum has transitioned to proof-of-stake (PoS), understanding how mining works remains essential for developers, node operators, and blockchain enthusiasts working with private or legacy networks. This guide explains how to start mining using geth, the official Go implementation of the Ethereum protocol.
We’ll walk through the core components involved in launching a miner, configuring mining parameters, and triggering the mining process via command-line flags, console commands, or RPC APIs—all while maintaining system integrity and performance.
Understanding the Miner Instance
The mining functionality in geth is encapsulated within a Miner instance, which serves as the primary interface for controlling block production. When geth starts, it automatically initializes this Miner object and places it in a ready state—waiting for an explicit command to begin mining.
This design allows flexible control: mining doesn’t start by default, giving users time to configure settings before committing computational resources.
// eth/backend.go:197
eth.miner = miner.New(eth, chainConfig, eth.EventMux(),
eth.engine, config.MinerRecommit,
config.MinerGasFloor, config.MinerGasCeil, eth.isLocalBlock)
eth.miner.SetExtra(makeExtraData(config.MinerExtraData))As shown above, only a few configuration options are required at initialization:
- Chain configuration
- Consensus engine
- Recommit interval
- Gas floor and ceiling targets
Once instantiated, the Miner can be controlled through private APIs—ensuring that only authorized users can initiate or modify mining operations.
👉 Learn how blockchain mining integrates with modern crypto platforms.
Configuring Mining Parameters
To optimize performance and control behavior, miners can adjust various runtime parameters. These settings are defined in cmd/utils/flags.go and influence everything from thread count to block rewards.
Here are key mining-related flags:
--mine: Enables automatic mining (default:false)--miner.threads: Number of threads for parallel PoW computation--miner.gasprice: Minimum gas price for transaction inclusion (default: 1 Gwei)--miner.gastarget/--miner.gaslimit: Lower and upper bounds for dynamic gas limit adjustment--miner.etherbase: Account to receive mining rewards (defaults to first local account)--miner.extradata: Custom data written into the block header--miner.recommit: Time interval to recompute and restart mining (default: 3s)--miner.noverify: Skips PoW verification (useful for testing)
Deprecated flags such as --minerthreads and --targetgaslimit should be avoided in favor of their modern equivalents.
You can list all mining-related options by running:
geth -h | grep "mine"Properly tuning these parameters ensures efficient resource utilization—especially important when running nodes on constrained hardware.
Starting Mining via Command-Line Flags
The simplest way to start mining is by using the --mine flag at startup. This tells geth to begin block production immediately upon launch.
For example, in developer mode, you can spin up a local testnet with instant mining enabled:
dgeth --dev --mine --datadir ./mychainIn this mode:
- A genesis block is created instantly
- Mining begins automatically
- No network peers are needed (
--maxpeers=0is implied)
Behind the scenes, geth checks whether --mine or --dev is set. If so, it:
- Validates that the node isn't a light client (which cannot mine)
- Sets the gas price in the transaction pool
- Assigns the number of mining threads
- Calls
ethereum.StartMining(threads)
If any step fails, the process halts with an error message—ensuring robust operation.
Launching Mining via JavaScript Console
After starting geth without auto-mining, you can manually trigger mining through the built-in JavaScript console.
First, launch geth with console access:
dgeth --maxpeers=0 consoleThen start mining with a single thread:
miner.start(1)This command invokes the internal miner_start RPC method with one worker thread. You'll see logs indicating new blocks being mined.
Other ways to call this API include:
| Environment | Syntax |
|---|---|
| Go client | miner.Start(threads *rpc.HexNumber) |
| Console | miner.start(number) |
| JSON-RPC | {"method": "miner_start", "params": [number]} |
Using the console gives real-time control and is ideal for debugging or interactive development.
👉 Discover how crypto networks use mining logic in next-gen applications.
Remote Mining Control via RPC API
For automation or integration into external tools, mining can be controlled remotely using JSON-RPC.
Enable the RPC server with appropriate APIs:
dgeth --maxpeers=0 --rpc --rpcapi "eth,admin,miner" --rpcport 8080 consoleNow send a request to start mining:
curl -d '{"id":1,"method":"miner_start","params":[1]}' \
-H "Content-Type: application/json" \
http://127.0.0.1:8080This approach enables headless operation and integration with monitoring dashboards or orchestration systems.
What Happens When Mining Starts?
Regardless of how you trigger it—flag, console, or RPC—the process converges on Ethereum.StartMining().
Here’s what happens under the hood:
- Thread Configuration: If the consensus engine supports threading (e.g., Ethash), it sets the number of threads.
- Gas Price Setup: The transaction pool enforces the configured minimum gas price.
- Coinbase Validation: Ensures the
etherbase(reward address) exists locally. - PoA Special Handling: For Clique (proof-of-authority), the wallet must sign blocks using the authorized key.
- Transaction Acceptance: Enables the node to accept and process incoming transactions.
- Worker Activation: Finally, it calls
miner.Start(eb)to kick off block production.
Inside the miner:
func (self *Miner) Start(coinbase common.Address) {
atomic.StoreInt32(&self.shouldStart, 1)
self.SetEtherbase(coinbase)
if atomic.LoadInt32(&self.canStart) == 0 {
log.Info("Network syncing, will start miner afterwards")
return
}
self.worker.start()
}The worker listens on a channel (startCh) and triggers block assembly once signaled.
Worker Signal Flow
When startCh receives a signal:
case <-w.startCh:
clearPending(w.chain.CurrentBlock().NumberU64())
timestamp = time.Now().Unix()
commit(false, commitInterruptNewHead)This initiates the creation of a new block based on pending transactions and current state.
Frequently Asked Questions
Q: Can I mine on a light client?
A: No. Light clients do not store full blockchain data and cannot perform mining. Use a full node instead.
Q: What does --miner.noverify do?
A: It disables PoW solution verification, useful for testing but should never be used in production.
Q: Why does my miner not start even after calling miner.start()?
A: The node might still be syncing. Mining only starts once synchronization is complete.
Q: Is GPU mining supported in geth?
A: Geth only supports CPU mining. For GPU mining, third-party tools like Ethminer are required.
Q: How do I stop mining?
A: Use miner.stop() in the console or call {"method": "miner_stop", "params": []} via RPC.
Q: Can I change the etherbase while mining?
A: Yes. Use miner.setEtherbase("0x...") before starting or restart mining after changing it.
👉 Explore how blockchain mining concepts apply to today’s leading crypto ecosystems.
Final Thoughts
Starting mining in geth involves more than just flipping a switch—it requires proper configuration, awareness of system state, and understanding of underlying mechanics. Whether you're setting up a local development environment or managing a private network, mastering these fundamentals ensures reliable and secure operation.
By leveraging command-line flags, interactive consoles, or remote APIs, you gain full control over your node’s behavior—all while adhering to best practices in performance and security.
Core Keywords: mining, geth, Ethereum, miner start, PoW, blockchain, console command, RPC API