<p>This is a known issue: <a href="https://github.com/input-output-hk/cardano-node/issues/3360" rel="nofollow noreferrer">https://github.com/input-output-hk/cardano-node/issues/3360</a></p>
<p>Out of curiosity, how many NFT's do you have per --tx-in? I've seen this increase memory usage dramatically with users on jpg.store who store a lot of NFT's in there wallet.</p>
<p>I have a few suggestions, knowing practically nothing about how this stuff works :P I'll share these in the Github issue as well.</p>
<ol>
<li><p>Can we remove these limits entirely? Is there any reason why a user can't just pay more to execute a tx with higher mem/CPU requirements?</p>
</li>
<li><p>If #1 isn't possible, what is the reason for keeping the limits as low as they are currently?</p>
</li>
<li><p>Are there any efforts to optimize the Plutus compiler here? Surely adding a few more --tx-in's shouldn't blow up memory like this?</p>
</li>
</ol>

CC BY-SA 4.0
2021-12-28T17:58:26.763Z
Thanks for the answer! well, these issues are only related. In the link you posted, I believe it is a simple transaction. This one is a transaction involving validator script. Also it is not NFT's. It's utxo's containing ADA or other CNT's, the main difference being the script inclusion in the transaction.
serx
CC BY-SA 4.0
2022-01-09T03:05:43.130Z
If the network had no computational bounds and was run on nuclear energy sure, but a lot of the nodes are people struggling to keep up with the current, ever increasing minimum requirements, and a lot of that energy is spinning turbines with steam from burning stuff. I don't understand why the contracts can't be iterated through... The network parameters are always known. If you can move them out in piecemeal then while it's a bug, it's not a blackhole.
Louis Waweru
CC BY-SA 4.0
2021-12-28T17:12:18.293Z
2021-12-28T17:12:18.293Z
Blake Brown
<p>Let's imagine I have AlwaysSucceeds Plutus validator script, which is:</p>
<pre><code>mkValidator :: Params -&gt; Datum -&gt; Redeemer -&gt; ScriptContext -&gt; Bool
mkValidator _ _ _ _ = True
</code></pre>
<p>I locked many different utxos at the script address in the testnet. Let's image 15 in total. Now I want to spend all of those utxos at once from the script using cardano-cli.
Building transaction as usual, and providing those utxos as --tx-in:</p>
<pre><code>--tx-in &quot;abcdef#1&quot; \
--tx-in-script-file alwaysSucceeds.plutus \
--tx-in-datum-value 420 \
--tx-in-redeemer-file redeemer.json \
--tx-in &quot;abcdef#2&quot; \
--tx-in-script-file alwaysSucceeds.plutus \
--tx-in-datum-value 420 \
--tx-in-redeemer-file redeemer.json \
...
...
--tx-in &quot;abcdef#15&quot; \
--tx-in-script-file alwaysSucceeds.plutus \
--tx-in-datum-value 420 \
--tx-in-redeemer-file redeemer.json \
</code></pre>
<p>I am pretty sure, that script is included only once in the transaction (is it?). Then submitting transaction to the testnet, I get the following error:</p>
<pre><code>Command failed: transaction submit  Error: Error while submitting tx: ShelleyTxValidationError ShelleyBasedEraAlonzo (ApplyTxError [UtxowFailure (WrappedShelleyEraFailure (UtxoFailure (ExUnitsTooBigUTxO (ExUnits {exUnitsMem = 12500000, exUnitsSteps = 10000000000}) (ExUnits {exUnitsMem = 31256460, exUnitsSteps = 14103266205}))))])
</code></pre>
<p>This basically means that I exceeded memory limit by 3 times and CPU by 1.5.</p>
<p>When lowering utxo count to 14,13... it scales down pretty much linearly:</p>
<pre><code>15 utxos: {exUnitsMem = 31256460, exUnitsSteps = 14103266205}
14: {exUnitsMem = 28008316, exUnitsSteps = 12629952076}
13: {exUnitsMem = 24926512, exUnitsSteps = 11232794573}
12: {exUnitsMem = 22011048, exUnitsSteps = 9911793696}
11: {exUnitsMem = 19261924, exUnitsSteps = 8666949445}
10: {exUnitsMem = 16679140, exUnitsSteps = 7498261820}
9: {exUnitsMem = 14262696, exUnitsSteps = 6405730821}
8: Transaction successfully submitted.
</code></pre>
<p>The validator script itself has no logic, it should not inflate memory and CPU usage (even though unfortunately it will be executed same amount of times as there are utxos).</p>
<p>My questions:</p>
<ol>
<li>Does this really mean that somewhat around 10 inputs are the maximum possible to spend from the script?</li>
<li>Is there any way to overcome this, and allow way more inputs from the script to be spent at once?</li>
<li>Are exUnitsMem and exUnitsSteps the same on the mainnet?</li>
<li>Maybe there is a way to increase those parameters to be able to submit the transaction?</li>
<li>Is script really included only once then submitting/Am I building transaction correctly?</li>
<li>As I am validating multiple utxos at once, is it possible to run validator only once and not for each utxo?</li>
<li>If this is really the limit, how we are supposed to build something useful? When and by how much are those units are planned to increase?</li>
<li>Is there any plans, regarding running validator only once for all utxo set, instead of executing it for each utxo?</li>
</ol>
<p>EDIT:</p>
<p>after updating node version to 1.32.1, error is thrown on the build step also, then utxo count is increased even further. Result is pretty much the same, only the error message is different:</p>
<pre><code>Command failed: transaction build  Error: The following scripts have execution failures:
the script for transaction input 0 (in the order of the TxIds) failed with:
The Plutus script evaluation failed: An error has occurred:  User error:
The budget was overspent. Final negative state: ({ cpu: 5931879314
| mem: -1199
})
</code></pre>

CC BY-SA 4.0
2021-12-28T10:39:19.120Z
You could deserialise the transaction and check how many times the script is included and how large it is. This would be interesting. I read that SundaeSwap struggled with the size of its scripts and had to do some low level optimisations. But unfortunately there are no details on this to be found.
Jey
CC BY-SA 4.0
2021-12-28T10:56:13.287Z
I am pretty sure that it is included only once, as signed transaction size is basically the same with either 1 or 15 utxos, and raw transaction size increases dramatically with each utxo. I can't think of any possible optimizations, as this seems to be lmited by design/architecture itself..
serx
CC BY-SA 4.0
2021-12-28T11:17:12.337Z
I understand now. It is not the transaction size constraint but the memory constraint that is hit here. I read in an article on iohk.io that the needed execution memory increases with every script-UTxO. I wondered on Twitter if the memory could not be cleared after each UTxO as they are independent of each other. I got no answer though and I don't know if this a yet unused optimisation or if something else is preventing this.
Jey
CC BY-SA 4.0
2021-12-28T11:19:49.843Z
Out of curiosity, how large is the transaction-cbor, though ?
Jey
CC BY-SA 4.0
2021-12-28T11:25:55.370Z
In my mind, the easiest solution for this would be to introduce some flag to allow executing validator script only once for the whole utxo input set and not for each utxo individually, as ScriptContext is aware of all of the utxos, and validation can be done in one iteration for all of them at once
serx
CC BY-SA 4.0
2021-12-28T11:36:18.360Z
transaction with my script (not AlwaysSuceeds), containing 10 utxo inputs, (and some other stuff) - {exUnitsMem = 19785600, exUnitsSteps = 8451556350}, built transaction - 104553 bytes, signed - 12619 bytes
serx
CC BY-SA 4.0
2021-12-28T11:48:29.233Z
found here: https://forum.cardano.org/t/max-number-of-transaction-inputs/60023/3, that each --tx-in generally uses about 38 bytes, so transaction size is not the main problem here, even though the utxo input limit is still somewhere in the hundreds for that limitation.
serx
CC BY-SA 4.0
2021-12-28T11:50:37.520Z
A script that always succeeds is a very special case. Optimisation this is certainly possible but I doubt if it is worthwhile.
Jey
CC BY-SA 4.0
2021-12-28T11:58:47.673Z
Well it's the simplest possible script. Any further logic would additionally increase memory and CPU. From transaction building side, what else can we really do? And in general, I don't think this should be solved by optimizing individually, rather addressed by Cardano themselves, as this will be a blocker for many just a little bit more complicated use cases
serx
CC BY-SA 4.0
2021-12-28T12:04:34.720Z
I don't think we can do anything here. It looks to me like these memory and cpu consumptions are the result of some overhead to set up script execution (load redeemer, datum, and context). It is difficult to tell. Maybe it is possible to simplify the compiled Plutus code further and reduce resource consumption.
Jey
<plutus><cardano-cli>
Transaction memory and cpu usage limits
# Transaction memory and cpu usage limits

(Asked by: username_0 on 2021-12-28)

Let's imagine I have AlwaysSucceeds Plutus validator script, which is:
mkValidator :: Params -> Datum -> Redeemer -> ScriptContext -> Bool
mkValidator _ _ _ _ = True

I locked many different utxos at the script address in the testnet. Let's image 15 in total. Now I want to spend all of those utxos at once from the script using cardano-cli.
Building transaction as usual, and providing those utxos as --tx-in:
--tx-in "abcdef#1" \
--tx-in-script-file alwaysSucceeds.plutus \
--tx-in-datum-value 420 \
--tx-in-redeemer-file redeemer.json \
--tx-in "abcdef#2" \
--tx-in-script-file alwaysSucceeds.plutus \
--tx-in-datum-value 420 \
--tx-in-redeemer-file redeemer.json \
...
...
--tx-in "abcdef#15" \
--tx-in-script-file alwaysSucceeds.plutus \
--tx-in-datum-value 420 \
--tx-in-redeemer-file redeemer.json \

I am pretty sure, that script is included only once in the transaction (is it?). Then submitting transaction to the testnet, I get the following error:
Command failed: transaction submit  Error: Error while submitting tx: ShelleyTxValidationError ShelleyBasedEraAlonzo (ApplyTxError [UtxowFailure (WrappedShelleyEraFailure (UtxoFailure (ExUnitsTooBigUTxO (ExUnits {exUnitsMem = 12500000, exUnitsSteps = 10000000000}) (ExUnits {exUnitsMem = 31256460, exUnitsSteps = 14103266205}))))])

This basically means that I exceeded memory limit by 3 times and CPU by 1.5.
When lowering utxo count to 14,13... it scales down pretty much linearly:
15 utxos: {exUnitsMem = 31256460, exUnitsSteps = 14103266205}
14: {exUnitsMem = 28008316, exUnitsSteps = 12629952076}
13: {exUnitsMem = 24926512, exUnitsSteps = 11232794573}
12: {exUnitsMem = 22011048, exUnitsSteps = 9911793696}
11: {exUnitsMem = 19261924, exUnitsSteps = 8666949445}
10: {exUnitsMem = 16679140, exUnitsSteps = 7498261820}
9: {exUnitsMem = 14262696, exUnitsSteps = 6405730821}
8: Transaction successfully submitted.

The validator script itself has no logic, it should not inflate memory and CPU usage (even though unfortunately it will be executed same amount of times as there are utxos).
My questions:

Does this really mean that somewhat around 10 inputs are the maximum possible to spend from the script?
Is there any way to overcome this, and allow way more inputs from the script to be spent at once?
Are exUnitsMem and exUnitsSteps the same on the mainnet?
Maybe there is a way to increase those parameters to be able to submit the transaction?
Is script really included only once then submitting/Am I building transaction correctly?
As I am validating multiple utxos at once, is it possible to run validator only once and not for each utxo?
If this is really the limit, how we are supposed to build something useful? When and by how much are those units are planned to increase?
Is there any plans, regarding running validator only once for all utxo set, instead of executing it for each utxo?

EDIT:
after updating node version to 1.32.1, error is thrown on the build step also, then utxo count is increased even further. Result is pretty much the same, only the error message is different:
Command failed: transaction build  Error: The following scripts have execution failures:
the script for transaction input 0 (in the order of the TxIds) failed with:
The Plutus script evaluation failed: An error has occurred:  User error:
The budget was overspent. Final negative state: ({ cpu: 5931879314
| mem: -1199
})

**Tags:** plutus, cardano-cli
> **Comments:**
> **username_1**: You could deserialise the transaction and check how many times the script is included and how large it is. This would be interesting. I read that SundaeSwap struggled with the size of its scripts and had to do some low level optimisations. But unfortunately there are no details on this to be found.  
> **username_0**: I am pretty sure that it is included only once, as signed transaction size is basically the same with either 1 or 15 utxos, and raw transaction size increases dramatically with each utxo. I can't think of any possible optimizations, as this seems to be lmited by design/architecture itself..  
> **username_1**: I understand now. It is not the transaction size constraint but the memory constraint that is hit here. I read in an article on iohk.io that the needed execution memory increases with every script-UTxO. I wondered on Twitter if the memory could not be cleared after each UTxO as they are independent of each other. I got no answer though and I don't know if this a yet unused optimisation or if something else is preventing this.  
> **username_1**: Out of curiosity, how large is the transaction-cbor, though ?  
> **username_0**: In my mind, the easiest solution for this would be to introduce some flag to allow executing validator script only once for the whole utxo input set and not for each utxo individually, as ScriptContext is aware of all of the utxos, and validation can be done in one iteration for all of them at once  
> **username_0**: transaction with my script (not AlwaysSuceeds), containing 10 utxo inputs, (and some other stuff) - {exUnitsMem = 19785600, exUnitsSteps = 8451556350}, built transaction - 104553 bytes, signed - 12619 bytes  
> **username_0**: found here: https://forum.cardano.org/t/max-number-of-transaction-inputs/60023/3, that each --tx-in generally uses about 38 bytes, so transaction size is not the main problem here, even though the utxo input limit is still somewhere in the hundreds for that limitation.  
> **username_1**: A script that always succeeds is a very special case. Optimisation this is certainly possible but I doubt if it is worthwhile.  
> **username_0**: Well it's the simplest possible script. Any further logic would additionally increase memory and CPU. From transaction building side, what else can we really do? And in general, I don't think this should be solved by optimizing individually, rather addressed by Cardano themselves, as this will be a blocker for many just a little bit more complicated use cases  
> **username_1**: I don't think we can do anything here. It looks to me like these memory and cpu consumptions are the result of some overhead to set up script execution (load redeemer, datum, and context). It is difficult to tell. Maybe it is possible to simplify the compiled Plutus code further and reduce resource consumption.  

---

## 1 answers

### Answer by username_2 on 2021-12-28. Score: 2

This is a known issue: <https://github.com/input-output-hk/cardano-node/issues/3360>

Out of curiosity, how many NFT's do you have per --tx-in? I've seen this increase memory usage dramatically with users on jpg.store who store a lot of NFT's in there wallet.

I have a few suggestions, knowing practically nothing about how this stuff works :P I'll share these in the Github issue as well.

1. Can we remove these limits entirely? Is there any reason why a user can't just pay more to execute a tx with higher mem/CPU requirements?
2. If #1 isn't possible, what is the reason for keeping the limits as low as they are currently?
3. Are there any efforts to optimize the Plutus compiler here? Surely adding a few more --tx-in's shouldn't blow up memory like this?

> **Comments:**
> **username_0**: Thanks for the answer! well, these issues are only related. In the link you posted, I believe it is a simple transaction. This one is a transaction involving validator script. Also it is not NFT's. It's utxo's containing ADA or other CNT's, the main difference being the script inclusion in the transaction.  
> **username_3**: If the network had no computational bounds and was run on nuclear energy sure, but a lot of the nodes are people struggling to keep up with the current, ever increasing minimum requirements, and a lot of that energy is spinning turbines with steam from burning stuff. I don't understand why the contracts can't be iterated through... The network parameters are always known. If you can move them out in piecemeal then while it's a bug, it's not a blackhole.  

---

