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

Spending gas from contract's balance - proposed optional opcode for a contract #61

Closed
axic opened this issue Jan 25, 2016 · 27 comments
Closed
Labels

Comments

@axic
Copy link
Member

axic commented Jan 25, 2016

Currently the gas limit is defined and paid by the caller. This proposal is about adding an option to the VM to set an alternate gas limit and gas source (the contract) by means of executing a special opcode within the contract, e.g. PAYGAS <limit>

A simple use case: the contract decides that the caller is on the list of trusted sources (for example it is a token holder) and takes over paying the gas. Alternatively the gas limit provided by the caller is used until exhausted, before using the contract's balance. This would be especially useful at fallback entry points enabling simple transactions to interact with a contract.

As you can see this idea is a a very early stage and comments are more than welcome.

@axic axic changed the title Spending gas from contract's balance Spending gas from contract's balance - proposed optional opcode for a contract Jan 25, 2016
@VoR0220
Copy link
Member

VoR0220 commented Jan 25, 2016

ehhh...sounds like you'd need a very good reputation system involved inherently in the contract and it would make them quite complicated. I don't think I'd support this.

@karalabe
Copy link
Member

Not necessarily. The contract could maintain its own list of member to whom it covers the costs. E.g. if you do something monetized, then the more transactions you do with the contract the more it could take off your costs, possibly reaching almost only the call cost. I think this idea has merits but probably needs to be thought through well :)

Edit: The reason this might not be essential is because we could "emulate" this behavior by the contract refunding its processing costs before returning. Though that's quite hackish.

@VoR0220
Copy link
Member

VoR0220 commented Jan 25, 2016

Okay @karalabe so what you're saying is that it could choose different members to siphon off of in future calls and build up a kind of debt based system to enable cheaper calls to newcomers of a Dapp? Am I understanding you correctly? Is that the use case you had in mind or ones like it?

@obscuren
Copy link
Contributor

I've been thinking about this problem for a while and I came up with the following solution. What if the miners maintained a list of contracts that would pay the COINBASE if ran with 0 gas price transactions? This would mean that anyone, even if you don't own any ether, you could bootstrap any account (or even run a free service) or any service.

No need for additional opcodes or alteration to the protocol, just need to persuade miners to run certain "trusted" contracts of which they know will pay them regardless of gas price.

@VoR0220
Copy link
Member

VoR0220 commented Jan 25, 2016

that'll be dangerous if implemented incorrectly...has to be done perfectly.

@obscuren
Copy link
Contributor

@VoR0220 feel free to list your concerns.

One possible obstacle is if you'd use real ether (i.e. ether from the contract). Please note that it doesn't need to be, it could be anything. It could some pegged (or not) to some (sub)currency. That's the beauty of it all, we can implement whatever we want.

@chriseth
Copy link
Contributor

I think that with the abstraction EIP, all miners have to have a whitelist of entry-level contract code (patterns) they want to execute. My guess would be that it is safer to extend this whitelist with patterns like this over time, but it might be that this will not work for all use cases.

@karalabe
Copy link
Member

I could even partner up with a mining pool to execute transactions for free to my contract and I'll pay them in cash off Ethereum :)

@VoR0220
Copy link
Member

VoR0220 commented Jan 25, 2016

if my understanding is correct, these trusted contracts would essentially be creating a credit system. If that credit system fails under any circumstance miners get shafted, but remember miners aren't one body coming debating with each other whether or not to raise or accept something from somebody, they are a body of machines just saying we agree that these transactions have been processed and this code has been executed. Per reputation systems, and whether or not to accept certain ones, that could leave a healthy portion of miners getting the shaft in their decision if a large set of miners decide to take on the risk...and should they fail there's an attack on the miners who chose not to take the risk as the losses are effectively socialized.

@VoR0220
Copy link
Member

VoR0220 commented Jan 25, 2016

these are just my ramblings and thoughts currently. If somebody wants to explain how this could be sheltered from this form of attack I'm open to suggestions.

@axic
Copy link
Member Author

axic commented Jan 25, 2016

@VoR0220 it is entirely optional and this behaviour is turned off by default, no need for reputation databases. If the author of the contract deems that certain addresses (knowing by the time of writing the contract, or programatically deciding on what conditions lead to an address earning trust) are trustable, it can turn off this feature for calls originating from them.

The current proposal is that happens via an opcode, e.g. the sender still has to have enough gas to execute the contract up to the point this opcode is executed. No one outside of the contract can execute that opcode on behalf of it and the contract needs to have enough balance to cover it. PAYGAS must check that the supplied limit exceeds or equals the current balance held by the contract.

@VoR0220
Copy link
Member

VoR0220 commented Jan 25, 2016

So essentially having it so that rather than the user paying for it out of their account, the contract creates a store of ether, and from there, executes the code from its stockpile rather than the callers account? Is that what you're saying?

@axic
Copy link
Member Author

axic commented Jan 25, 2016

@VoR0220 but the contract still has a store of ether, doesn't it? Is that being removed?

@VoR0220
Copy link
Member

VoR0220 commented Jan 25, 2016

depends. I'd think you'd have to have a special balance tied to contracts that is completely separated from other balances of the contract for these purposes. You don't want contracts suddenly raiding your funds that you've entrusted it with (see modifiers). But I could see that being useful.

@axic
Copy link
Member Author

axic commented Jan 25, 2016

@VoR0220 that's why the limit must accompany the opcode. It is up to the contract then to decide when and how much limit he gives to a certain incoming transaction.

@VoR0220
Copy link
Member

VoR0220 commented Jan 25, 2016

interesting. But that only accounts for gas costs...you'd still need to put it as its own "reserve" so to speak. Or atleast enable ways to sequester that payment ability from other functions of the contract.

@axic
Copy link
Member Author

axic commented Apr 6, 2016

As an intermediate solution, @gavofyork suggested that a contract owner could have:

  • an arrangement with a specific miner to pay the costs through other means (e.g. by paying directly)
  • and setting the gas price to 0

While this is definitely doable, it is only a workaround.

@VoR0220
Copy link
Member

VoR0220 commented Apr 6, 2016

@axic I agree. That sounds like the pain in the dick method. Isn't there a way we could make this a trustless solution?

@axic
Copy link
Member Author

axic commented Apr 6, 2016

I still think the original proposal (which might have been slightly misinterpreted) makes sense.

As a concept take the following Solidity code. It is the fallback function, which is called when no data is being sent (i.e. regular value transfer):

contract Sample {
    function() {
        if (msg.sender == owner) {
            assembly { paygas(200000) }
            // do costly housekeeping
            return
        }

        // it isn't the owner, but we still do more than 21000 gas worth of execution
        // and lets cover the difference, but only if there's meaningful value being sent
        if (msg.value > 2 eth) {
            assembly { paygas(20000) }
            // do something
        }
    }
}

The above code could also decide to use different gas values based on what gas limit was provided by the caller. If paygas > totalgas, that means the contract is paying in full.

It also means that there must be enough gas limit supplied to reach and execute the code until and including the paygas instruction.

@VoR0220
Copy link
Member

VoR0220 commented Apr 6, 2016

I completely agree. I think this should be doable.

@gavofyork
Copy link

main issue with this is putting 10 ether in a contract and sending a tx that runs:

function() { paygas(10 ether); while (true) {} }

it will run OOG only after 4.7m (or whatever block gas limit is) of miner compute time is spent, yet nobody will end up paying anything since it'll be reverted.

basically, PAYGAS needs checkpointing to work safely.

@VoR0220
Copy link
Member

VoR0220 commented May 26, 2016

Well that's to be expected, yes. Any other specifics you might have in mind?

@Frostcoin
Copy link

I'm also running into this issue.
I basically need a contract that automatically sends deposits to other (unchangeable) accounts automatically. The deposits come from mining pools so from what i heard there is no way to be sure they pay enough gas to initiate the contract thus making it practically impossible to automatically split mining revenues without manual interaction.

@igorbarbashin
Copy link

igorbarbashin commented May 8, 2018

I believe the contract-sponsored transactions will have an enormous impact on overall user experience and can potentially widen the Ethereum adoption. As you don't have to have ETH to call certain methods in the contract if your address is white-listed in the contract.

I'm still a noob in Ethereum, so please tell me if the following proposal is possible. Essentially it is an incentive model for miners to include zero-gas-price transactions in a block.
This solution doesn't require a separate opcode.

  1. An end user creates a transaction with proper gas amount and zero gas price (tx1)
  2. The miner doesn't discard the transaction but checks if the contract the transaction is calling has a predefined rebate function and checks if conditions are met to get a refund
  3. The miner creates a new transaction (tx2) that calls the rebate function (the arguments are the hash of tx1 and miner's address)
  4. The miner includes both tx1 and tx2 in the block

Is it possible in theory?

@Gurkirat2210
Copy link

Gurkirat2210 commented Feb 7, 2019

This is exactly what I was thinking, i.e to charge user a fixed cost for services, and price services as per custom business model instead of data and execution cost. The contract will be responsible for managing transaction cost. The difference between cost charged and spent will be profit.

This also encourages devs to design optimal contracts to maximise gains

@github-actions
Copy link

There has been no activity on this issue for two months. It will be closed in a week if no further activity occurs. If you would like to move this EIP forward, please respond to any outstanding feedback or add a comment indicating that you have addressed all required feedback and are ready for a review.

@github-actions github-actions bot added the stale label Jan 17, 2022
@github-actions
Copy link

This issue was closed due to inactivity. If you are still pursuing it, feel free to reopen it and respond to any feedback or request a review in a comment.

bumblefudge added a commit to bumblefudge/EIPs that referenced this issue Feb 16, 2024
chore: fixes and improvements to solana caip10 and caip2
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests