diff --git a/docs/cadence/language/built-in-functions.mdx b/docs/cadence/language/built-in-functions.mdx index 375ebc7976..76d0cff20d 100644 --- a/docs/cadence/language/built-in-functions.mdx +++ b/docs/cadence/language/built-in-functions.mdx @@ -29,40 +29,49 @@ Use this function for internal sanity checks. The message argument is optional. -## `unsafeRandom` +## `revertibleRandom` ```cadence -fun unsafeRandom(): UInt64 +fun revertibleRandom(): UInt64 ``` Returns a pseudo-random number. - -Smart contract developers should be mindful about the limitations of unsafeRandom. -The stream of random numbers produced is potentially unsafe in the following two regards: +The sequence of returned random numbers is independent for +every transaction in each block. + +Under the hood, Cadence instantiates a cryptographically-secure pseudo-random number +generator (CSPRG) for each transaction independently, where the seeds of any two transactions +are different with near certainty. -1. The sequence of random numbers is potentially predictable by transactions within the same block -and by other smart contracts calling into your smart contract. -2. A transaction calling into your smart contract can potentially bias the sequence of random numbers which -your smart contract internally generates. +The random numbers returned are unpredictable +(unpredictable for miners at block construction time, +and unpredictable for cadence logic at time of call), +verifiable, as well as unbiasable by miners and previously-running Cadence code. +See [Secure random number generator for Flow’s smart contracts](https://forum.flow.com/t/secure-random-number-generator-for-flow-s-smart-contracts/5110) +and [FLIP120](https://github.com/onflow/flips/pull/120) for more details. -The Flow project is working towards removing these limitations incrementally. -Once Flow addressed these points and randomness is safe, -the "unsafe" qualifier is going to get removed. +Nevertheless, developers need to be mindful to use `revertibleRandom()` correctly. -Nevertheless, there is an additional safety-relevant aspect that developers need to be mindful about: + -A transaction can atomically revert all its actions at any time. -Therefore, it is possible for a transaction calling into a smart contract +A transaction can atomically revert all its action. +It is possible for a transaction submitted by an untrusted party to post-select favorable results and revert the transaction for unfavorable results. + + +The function usage remains safe when called by a trusted party that does not +perform post-selection on the returned random numbers. + This limitation is inherent to any smart contract platform that allows transactions to roll back atomically and cannot be solved through safe randomness alone. -Providing additional Cadence language primitives to simplify this challenge for developers is on the roadmap. -Nevertheless, with safe randomness, points 1 and 2 above resolved, -developers can prevent clients from post-select favorable outcomes using approaches such as described in the -[Smart Contract Security Best Practices](https://consensys.github.io/smart-contract-best-practices/development-recommendations/general/public-data/). - + +Flow protocol has suggested a [solution to implement safe +commit-reveal schemes](https://github.com/onflow/flips/pull/123) and address this limitation. +In cases where a non-trusted party can interact with smart contracts generating +random numbers through their own transactions, **use a commit-reveal scheme** +as described in this [rudimentary example](https://github.com/onflow/flips/blob/main/protocol/20230728-commit-reveal.md#tutorials-and-examples) ## `RLP` diff --git a/versioned_docs/version-stable/cadence/language/built-in-functions.mdx b/versioned_docs/version-stable/cadence/language/built-in-functions.mdx index 82c61fc5b9..6bebe636e1 100644 --- a/versioned_docs/version-stable/cadence/language/built-in-functions.mdx +++ b/versioned_docs/version-stable/cadence/language/built-in-functions.mdx @@ -30,37 +30,65 @@ fun assert(_ condition: Bool, message: String) The message argument is optional. -## unsafeRandom +## `revertibleRandom` ```cadence -fun unsafeRandom(): UInt64 +fun revertibleRandom(): UInt64 ``` - Returns a pseudo-random number. + +`unsafeRandom()` function currently behaves the same way as `revertibleRandom()`, +and will be deprecated in the next Cadence release. + - NOTE: - Smart contract developers should be mindful about the limitations of unsafeRandom. - The stream of random numbers produced is potentially unsafe in the following two regards: +Returns a pseudo-random number. - 1. The sequence of random numbers is potentially predictable by transactions within the same block - and by other smart contracts calling into your smart contract. - 2. A transaction calling into your smart contract can potentially bias the sequence of random numbers which - your smart contract internally generates. +The sequence of returned random numbers is independent for +every transaction in each block. - We are working towards removing these limitations incrementally. Once these points are addressed, - Flow’s randomness is safe and we will remove the "unsafe" qualifier. +Under the hood, Cadence instantiates a cryptographically-secure pseudo-random number +generator (CSPRG) for each transaction independently, where the seeds of any two transactions +are different with near certainty. - Nevertheless, there is an additional safety-relevant aspect that developers need to be mindful about: +The random numbers returned are unpredictable +(unpredictable for miners at block construction time, +and unpredictable for cadence logic at time of call), +verifiable, as well as unbiasable by miners and previously-running Cadence code. +See [Secure random number generator for Flow’s smart contracts](https://forum.flow.com/t/secure-random-number-generator-for-flow-s-smart-contracts/5110) +and [FLIP120](https://github.com/onflow/flips/pull/120) for more details. - * A transaction can atomically revert all its action at any time. Therefore, it is possible for a transaction calling into - your smart contract to post-select favourable results and revert the transaction for unfavourable results. - ([example](https://consensys.github.io/smart-contract-best-practices/development-recommendations/general/public-data/)) +Nevertheless, developers need to be mindful to use `revertibleRandom()` correctly. - This limitation is inherent to any smart contract platform that allows transactions to roll back atomically and cannot be - solved through safe randomness alone. Providing additional Cadence language primitives to simplify this challenge for - developers is on our roadmap as well. Nevertheless, with safe randomness (points 1 and 2 above resolved), developers can prevent - clients from post-select favourable outcomes using approaches such as described in the - [example](https://consensys.github.io/smart-contract-best-practices/development-recommendations/general/public-data/). + + +A transaction can atomically revert all its action. +It is possible for a transaction submitted by an untrusted party +to post-select favorable results and revert the transaction for unfavorable results. + + + +The function usage remains safe when called by a trusted party that does not +perform post-selection on the returned random numbers. + +This limitation is inherent to any smart contract platform that allows transactions to roll back atomically +and cannot be solved through safe randomness alone. + +Flow protocol has suggested a [solution to implement safe +commit-reveal schemes](https://github.com/onflow/flips/pull/123) and address this limitation. +In cases where a non-trusted party can interact with smart contracts generating +random numbers through their own transactions, **use a commit-reveal scheme** +as described in this [rudimentary example](https://github.com/onflow/flips/blob/main/protocol/20230728-commit-reveal.md#tutorials-and-examples) + + +## `unsafeRandom` + +This function is superseded by `revertibleRandom()`. +`unsafeRandom` has the same interface and implementation as `revertibleRandom()` although +it is called unsafe. + + +`unsafeRandom` is deprecated and will be removed in an upcoming release of Cadence. Use `revertibleRandom()` instead. + ## RLP