Consumo de gas en una cadena de transferencias internas
1 respuesta
- votos
-
- 2019-03-26
Nopuedeexcederel hard_gas_limit_per_operation=400000. Sinembargo,probablemente seincrementaráen futurosprotocolos (consulte,porejemplo,propuestas de" Atenas ").
Lastransferenciasinternaspueden consumirmuchogas.
Primero,hay un costofijo de 10000gasportransferencia.
En segundo lugar,y lo queesmásimportante,cuando se 'analiza' un contrato,el
código
yelalmacenamiento
completo del contrato se leen de labase de datos de Tezos (exceptoelmapa_grande
). Pagaelgas segúneltamañobinario de los datos leídos. Elcódigo
completotambién se 'analiza'paraextraereltipo deparámetro del contrato y compararlo coneltipoesperado. Esto sucedeen almenos dos lugares:- Cuandotenga
contractp
en sutipo dealmacenamiento
(fuera delbig_map
),el contrato se analizará antes de que seejecute su script. - Cuando su scriptejecute lainstrucción
CONTRACTp
Michelson,el contrato será analizado.
Entonces,esto significa queparapoder TRANSFER_TOKENS a un contratoescrito,debe analizarlo,pagandogasproporcionalmente a su código ytamaño de almacenamiento. Cuandoese contrato recibe latransferencia y se cargaparaejecutarse,este costo,ymás,sepagará nuevamente ,antes de queel script de destino comience aejecutarse.
(Es completamente innecesario queel
almacenamiento
se lea de labase de datos al analizar un contrato. Podríamos solucionarestotrivialmenteen unafutura actualización delprotocolo,y realmente debería,puede conducir a vulnerabilidadesmuy sorprendentes. Serámenosfácil solucionarelproblema concódigo
,peroespero que algún día se solucione,dividiendoel códigoen variaspartes de labase de datos. Quizásestopueda suceder cuando agreguemospuntos deentrada deprimera clase).Entonces,unaforma demitigarestoes asegurarse de que cada contratoinvolucradotenga un códigopequeño y almacenamiento,exceptoelbig_map. Solopagagasolinaporel contenido delbig_map cuando
OBTENGA
(ytal vezDESEMPAQUETE
).Desafortunadamente,estoparece significar que,hoyen día,laformamás óptima deescribir contratos complejos (especialmente cuando sonel destino de lastransferenciasinternas) será usar
big_mapbytesbytes
como almacenamiento,yparaponertodoel código yel almacenamiento dentro delbig_map,cargándolo apedido,usando UNPACK.You cannot exceed the hard_gas_limit_per_operation = 400000. It will probably be increased in future protocols, though (see e.g. the "Athens" proposals).
Internal transfers can use up a lot of gas.
First, there is a fixed cost of 10000 gas per transfer.
Second, and more importantly, when a contract is 'parsed', the contract's entire
code
andstorage
are read out of the Tezos database (except for thebig_map
). You pay gas according the binary size of the data read. The entirecode
is also 'parsed', in order to pull out the parameter type of the contract, and compare it to the expected type. This happens in at least two places:- When you have
contract p
in yourstorage
type (outside of thebig_map
), the contract will be parsed before your script runs. - When your script executes the
CONTRACT p
Michelson instruction, the contract will be parsed.
So, this means that in order to TRANSFER_TOKENS to a scripted contract, you must parse it, paying gas proportional to its code and storage size. When that contract receives the transfer and is loaded to be executed, this cost, and more, will be paid again, before the destination script even starts running.
(It is completely unnecessary for the
storage
to be read from the database when parsing a contract. We could fix this trivially in a future protocol upgrade -- and we really should, it can lead to very surprising vulnerabilities. It will be less easy to fix the problem withcode
, but I expect it will be fixed someday, by splitting the code into several pieces in the database. Maybe this can happen when we add first-class entry points.)So, one way to mitigate this is to make sure that every contract involved has small code and storage -- except for the big_map. You only pay gas for the contents of the big_map when you
GET
(and maybeUNPACK
) them.Unfortunately, this seems to mean that, today, the most optimal way to write complex contracts (especially when they are the destination for internal transfers) will be to use
big_map bytes bytes
as storage, and to put all the code and storage inside the big_map, loading it on demand, using UNPACK.-
Gracias,votaré afavor de la respuesta una vez que confirme através de --dry-run queel costo delgasestá aumentandoel límiteestándaren esta cadena de llamadasinternas.Thanks, I'll upvote the answer once I confirm via --dry-run that gas cost is increasing the standard limit in this chain of internal calls.
- 0
- 2019-03-28
- user_184
-
Noesterriblemente utilizable,perotengaen cuenta quetambiénpuede usar `tezos-client run scriptfoo.tzen el almacenamiento 'Emparejar lo que sea'e ingresar 'lo que sea' --track-stack`,lo que lepermitirá verelgas restanteencadapaso.It's not terribly usable, but note that you can also use `tezos-client run script foo.tz on storage 'Pair whatever whatever' and input 'whatever' --track-stack`, which will allow you to see the remaining gas at each step.
- 0
- 2019-03-28
- Tom
-
Parece que --track-stacknofunciona oestá obsoleto.Me saleel siguienteerror: "Opción de línea de comandoinesperada --track-stack". Sinembargo,como señaló,el límite degases agotador.Seems like --track-stack doesn't work or deprected. I get following error : "Unexpected command line option --track-stack." However, As you pointed out , gas limit is exhausting.
- 0
- 2019-04-17
- user_184
-
Uy,errortipográfico,es --trace-stackoops, typo, it's --trace-stack
- 0
- 2019-04-17
- Tom
-
sí,esofunciona.Aunque han agregado los detallesproporcionadosporestabandera deformapredeterminadaen los registros defallas.yep, that works. Though they have added the details provided by this flag by default in failure logs.
- 0
- 2019-04-17
- user_184
Estoyintentando realizar una cadena de llamadaspor contrato contransferenciasinternas.
Creo quemis contratos actuales sonmuy simples,perome quedo singasolina después de solo 4transferenciasinternas:
Cuando las llamadasinvolucradas sean complejas,nome seráposible realizar llamadasentre dos otres contratos si sigo recibiendoelerror de agotamiento degas.
¿Qué causaesto? ¿Hay algo quepueda hacer al respecto?