Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

core/types: more easily extensible tx signing #30372

Merged
merged 2 commits into from
Sep 16, 2024

Conversation

piersy
Copy link
Contributor

@piersy piersy commented Aug 30, 2024

Having just a single return point in methods that build signers makes it easier for forks of go ethereum to add their own signers that delegate to the underlying signer chain, since they can intercept the signer chain at a single point.

At celo we are currently transitioning to be an L2 based on the optimism codebase and we have a number of additional transaction types that we have extended vanilla ethereum with, these transaction types require custom signing therefore requiring us to modify the signer creation functions.

In order to lessen the burden of being a fork of op-geth and consequently go-ethereum we are trying to ensure that our changes are minimally invasive to the codebase, we've partially achieved that for transaction signing by having an overlay signer that handles our added transactions and delegates to the existing signer chain for all other cases.

In the case of MakeSigner(see below) we are able to cleanly add this since we can delegate to the signer variable, however for LatestSigner and LatestSignerForChainId this is not possible due to the multiple return points.

// MakeSigner returns a Signer based on the given chain config and block number.
func MakeSigner(config *params.ChainConfig, blockNumber *big.Int, blockTime uint64) Signer {
	var signer Signer
	switch {
	case config.IsCancun(blockNumber, blockTime) && !config.IsOptimism():
		signer = NewCancunSigner(config.ChainID)
	case config.IsLondon(blockNumber):
		signer = NewLondonSigner(config.ChainID)
	case config.IsBerlin(blockNumber):
		signer = NewEIP2930Signer(config.ChainID)
	case config.IsEIP155(blockNumber):
		signer = NewEIP155Signer(config.ChainID)
	case config.IsHomestead(blockNumber):
		signer = HomesteadSigner{}
	default:
		signer = FrontierSigner{}
	}

	// Apply the celo overlay signer, if no celo forks have been enabled then the given signer is returned.
	signer = makeCeloSigner(config, blockTime, signer)

	return signer
}

Having multiple return points requires us to handle potentially every return point inside the switch case or if ladder, which further introduces conflicts when forks with new signing are introduced.

I'm aware that this change doesn't bring any direct benefit for the go-ethereum codebase, but also I don't think it is further complicating the codebase and should help to simplify the lives of fork maintainers.

Having just a single return point in methods that build signers makes it
easier for forks of go ethereum to add their own signers that delegate
to the underlying signer chain, since they can intercept the signer
chain at a single point.
@fjl fjl self-assigned this Aug 30, 2024
}
}
return HomesteadSigner{}
return signer
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The way you did this, you always instantiate the default, then instantiate the non-default. IMO let's instantiate only once, e.g. by doing

	var signer Signer
	if config.ChainID != nil {
		switch {
		case config.CancunTime != nil:
			signer = NewCancunSigner(config.ChainID)
		case config.LondonBlock != nil:
			signer = NewLondonSigner(config.ChainID)
		case config.BerlinBlock != nil:
			signer = NewEIP2930Signer(config.ChainID)
		case config.EIP155Block != nil:
			signer = NewEIP155Signer(config.ChainID)
		default:
			signer = HomesteadSigner{}
		}
	} else {
		signer = HomesteadSigner{}
	}
	return signer

Copy link
Contributor Author

@piersy piersy Sep 6, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi @holiman, good point. I felt it was a little cleaner without the extra else but I wasn't considering instantiations at the time. Will update.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi @holiman, just letting you know I have made the changes you suggested.

Copy link
Contributor

@holiman holiman left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@holiman holiman added this to the 1.14.9 milestone Sep 16, 2024
@holiman holiman merged commit 0342496 into ethereum:master Sep 16, 2024
3 checks passed
@piersy piersy deleted the more-easily-extendible-tx-signing branch September 16, 2024 08:29
This pull request was closed.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants