¿Qué tan seguro es usar block.timestamp como tiempo de vencimiento del contrato? Si un minero proporciona una marca de tiempo incorrecta en el encabezado de un bloque, ¿cuánto puede estar mal antes de que otros nodos lo rechacen? ¿Hay alguna estrategia para hacer un contrato más robusto a esto?
No especialmente , pero depende de cuál sea el caso de uso.
Los tiempos de bloque están sujetos a las siguientes restricciones:
En conjunto, estos factores sugieren que la mayoría de los bloques producidos por pequeños mineros de hashrate que no intentan manipular nada serán bastante precisos. Sin embargo, es trivial para un minero más poderoso manipular las marcas de tiempo durante períodos cortos , especialmente si hay algo que ganar al hacer esto.
Ultimate, no hay una forma criptográfica de verificar la marca de tiempo en sí, solo el orden de ciertas estructuras criptográficas . Por lo tanto, block.timestamp debe complementarse con alguna otra estrategia en el caso de aplicaciones de alto valor/riesgo.
Primero, un básico: el uso de la igualdad estricta == block.timestamp
no sería seguro, ya que un bloque con esa marca de tiempo exacta nunca podría ser minado. Así que usa>= block.timestamp
Ahora depende de lo que suceda cuando se alcance el "tiempo de vencimiento" del contrato . Por razones similares al uso seguro de BLOCKHASH , block.timestamp
solo debe usarse de manera segura si la cantidad total de valor que descansa sobre lo que hace el contrato en el "tiempo de vencimiento" es inferior a lo que gana un minero al extraer un solo bloque. Si el resultado de una lotería que vale millones depende de block.timestamp
, la marca de tiempo probablemente será manipulada.
El Libro Amarillo no tiene ninguna respuesta a "cuánto puede estar apagado antes de que otros nodos lo rechacen". Si block.timestamp
se utiliza, la única garantía (ecuación 43) es que block.timestamp
sea mayor que la de su matriz. Pero hay razones teóricas de juegos por las block.timestamp
que no estarán significativamente equivocados.
De los documentos de Solidity , otra cosa a tener en cuenta es: publica una transacción en un momento X, esta transacción contiene un código que llama block.timestamp
y se incluye en un bloque cuya marca de tiempo es Y y este bloque se incluye en la cadena canónica (publicado) en un tiempo Z. El valor de block.timestamp
será idéntico a Y, y X <= Y <= Z
Una solución más segura sería confiar en block.number y un tiempo estimado por incremento de bloque. Supongamos que desea crear un arrendamiento para un contrato con una fecha de finalización específica. Podrías calcular el tiempo aproximado con:
estimated_time_in_blocks = lease_length_in_seconds / average_block_time_in_seconds
lease_end_block_number = current_block + estimated_time_in_blocks
En su contrato puede verificar:
block.number <= lease_end_block_number
El ejemplo en Mastering Ethereum es:
con un tiempo de bloque de 10 segundos, 1 semana equivale a aproximadamente 60480 bloques. Por lo tanto, especificar un número de bloque en el que cambiar el estado de un contrato puede ser más seguro, ya que los mineros no pueden manipular fácilmente el número de bloque.
El contrato BAT ICO utiliza este enfoque
jeff coleman
ética