Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/master' into dev-ghc-9.6
Browse files Browse the repository at this point in the history
  • Loading branch information
elopez committed Jul 25, 2024
2 parents 04b9d05 + a550094 commit e64a2a9
Show file tree
Hide file tree
Showing 43 changed files with 632 additions and 406 deletions.
2 changes: 1 addition & 1 deletion .github/container-linux-static/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,5 @@ This container is used as part of `.github/workflows/ci.yml` to produce
statically-linked amd64 linux builds of Echidna. It is based on the following
container produced by FP Complete and maintained in the
[`fpco/alpine-haskell-stack`](https://github.com/fpco/alpine-haskell-stack/tree/ghc927)
repository, and contains a few extra dependencies and configuration to make it
repository, and contains a few extra dependencies and configurations to make it
suitable for the GitHub Actions environment.
4 changes: 2 additions & 2 deletions .github/workflows/docker.yml
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,7 @@ jobs:
password: ${{ secrets.DOCKERHUB_ACCESS_TOKEN }}

- name: Docker Build and Push (Ubuntu & NVM variant)
uses: docker/build-push-action@v5
uses: docker/build-push-action@v6
with:
platforms: linux/amd64
target: final-ubuntu
Expand All @@ -74,7 +74,7 @@ jobs:
cache-to: type=gha,mode=max

- name: Docker Build and Push (Distroless variant)
uses: docker/build-push-action@v5
uses: docker/build-push-action@v6
if: ${{ env.WORKFLOW_BUILD_DISTROLESS == true }}
with:
platforms: linux/amd64
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/hlint.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ jobs:
uses: actions/checkout@v4

- name: Install Nix
uses: cachix/install-nix-action@v26
uses: cachix/install-nix-action@V27
with:
nix_path: nixpkgs=channel:nixos-unstable

Expand Down
12 changes: 6 additions & 6 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -36,16 +36,16 @@ jobs:
uses: actions/checkout@v4

- name: Install Nix
uses: DeterminateSystems/nix-installer-action@v11
uses: DeterminateSystems/nix-installer-action@v13

- name: Configure Cachix
uses: cachix/cachix-action@v14
uses: cachix/cachix-action@v15
with:
name: trailofbits
authToken: ${{ secrets.CACHIX_AUTH_TOKEN }}

- name: Configure Nix cache
uses: DeterminateSystems/magic-nix-cache-action@v6
uses: DeterminateSystems/magic-nix-cache-action@v7
with:
upstream-cache: https://trailofbits.cachix.org

Expand Down Expand Up @@ -96,15 +96,15 @@ jobs:
merge-multiple: true

- name: Sign binaries
uses: sigstore/gh-action-sigstore-python@v2.1.1
uses: sigstore/gh-action-sigstore-python@v3.0.0
with:
inputs: ./echidna-*.tar.gz

- name: Create GitHub release and upload binaries
uses: softprops/[email protected].5
uses: softprops/[email protected].8
with:
draft: true
name: "Echidna ${{ needs.nixBuild.outputs.version }}"
files: |
./echidna-*.tar.gz
./echidna-*.tar.gz.sigstore
./echidna-*.tar.gz.sigstore.json
11 changes: 11 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,14 @@
## 2.2.4

* Initial TLOAD/TSTORE support (#1286)
* Initial symbolic execution implementation (experimental, #1216, #1251, #1285)
* New panel toggles in the UI (#1197)
* New gas/s metric (#1279)
* Improved logging (#1202, #1271, #1273, #1274, #1283, #1258, #1269)
* Performance improvements with multiple workers (#1228)
* Shrinking improvements (#1196, #1250, #1280)
* Improved configuration options (#1200, #1227, #1251)

## 2.2.3

* feat: add CLI commands for RPC URL and block number (#1194)
Expand Down
2 changes: 1 addition & 1 deletion CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ appreciate all contributions, including bug reports, feature suggestions,
tutorials/blog posts, and code improvements.

If you're unsure where to start, we recommend to join our [chat room](https://slack.empirehacking.nyc/)
(in the #ethereum channel) to discuss new ideas to improve this tool. You can also take a look to the [`help wanted`](https://github.com/crytic/echidna/issues?q=is%3Aissue+is%3Aopen+label%3A%22help+wanted%22)
(in the #ethereum channel) to discuss new ideas to improve this tool. You can also take a look at the [`help wanted`](https://github.com/crytic/echidna/issues?q=is%3Aissue+is%3Aopen+label%3A%22help+wanted%22)
issue labels.

## Bug reports and feature suggestions
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -172,7 +172,7 @@ Common causes for performance issues that we observed:
- Lazy data constructors that accumulate thunks
- Inefficient data structures used in hot paths

Checking for these is a good place to start. If you suspect some comuptation is too lazy and
Checking for these is a good place to start. If you suspect some computation is too lazy and
leaks memory, you can use `force` from `Control.DeepSeq` to make sure it gets evaluated.

## Limitations and known issues
Expand Down
64 changes: 33 additions & 31 deletions lib/Echidna.hs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ module Echidna where
import Control.Concurrent (newChan)
import Control.Monad.Catch (MonadThrow(..))
import Control.Monad.ST (RealWorld)
import Data.IORef (writeIORef, newIORef)
import Data.IORef (newIORef)
import Data.List (find)
import Data.List.NonEmpty (NonEmpty)
import Data.List.NonEmpty qualified as NE
Expand All @@ -13,25 +13,26 @@ import System.FilePath ((</>))

import EVM (cheatCode)
import EVM.ABI (AbiValue(AbiAddress))
import EVM.Dapp (DappInfo(..), dappInfo)
import EVM.Dapp (dappInfo)
import EVM.Fetch qualified
import EVM.Solidity (BuildOutput)
import EVM.Solidity (BuildOutput(..), Contracts(Contracts))
import EVM.Types hiding (Env)

import Echidna.ABI
import Echidna.Etheno (loadEtheno, extractFromEtheno)
import Echidna.Onchain as Onchain
import Echidna.Output.Corpus
import Echidna.SourceAnalysis.Slither
import Echidna.Solidity
import Echidna.Symbolic (forceAddr)
import Echidna.Test (createTests)
import Echidna.Types.Campaign
import Echidna.Types.Config
import Echidna.Types.Random
import Echidna.Types.Signature
import Echidna.Types.Solidity
import Echidna.Types.Tx
import Echidna.Types.World
import Echidna.Types.Test (EchidnaTest)
import Echidna.Types.Signature (ContractName)

-- | This function is used to prepare, process, compile and initialize smart contracts for testing.
-- It takes:
Expand All @@ -45,17 +46,20 @@ import Echidna.Types.World
-- * A list of Echidna tests to check
-- * A prepopulated dictionary
prepareContract
:: Env
:: EConfig
-> NonEmpty FilePath
-> BuildOutput
-> Maybe ContractName
-> Seed
-> IO (VM Concrete RealWorld, World, GenDict)
prepareContract env solFiles specifiedContract seed = do
let solConf = env.cfg.solConf
contracts = Map.elems env.dapp.solcByName
-> IO (VM Concrete RealWorld, Env, GenDict)
prepareContract cfg solFiles buildOutput selectedContract seed = do
let solConf = cfg.solConf
(Contracts contractMap) = buildOutput.contracts
contracts = Map.elems contractMap

-- deploy contracts
(vm, funs, testNames, signatureMap) <- loadSpecified env specifiedContract contracts
mainContract <- selectMainContract solConf selectedContract contracts
tests <- mkTests solConf mainContract
signatureMap <- mkSignatureMap solConf mainContract contracts

-- run processors
slitherInfo <- runSlither (NE.head solFiles) solConf
Expand All @@ -64,16 +68,14 @@ prepareContract env solFiles specifiedContract seed = do
Just version -> throwM $ OutdatedSolcVersion version
Nothing -> pure ()

let
-- load tests
echidnaTests = createTests solConf.testMode
solConf.testDestruction
testNames
(forceAddr vm.state.contract)
funs
let world = mkWorld cfg.solConf signatureMap selectedContract slitherInfo contracts

world = mkWorld solConf signatureMap specifiedContract slitherInfo contracts
env <- mkEnv cfg buildOutput tests world

-- deploy contracts
vm <- loadSpecified env mainContract contracts

let
deployedAddresses = Set.fromList $ AbiAddress . forceAddr <$> Map.keys vm.env.contracts
constants = enhanceConstants slitherInfo
<> timeConstants
Expand All @@ -88,13 +90,12 @@ prepareContract env solFiles specifiedContract seed = do
seed
(returnTypes contracts)

writeIORef env.testsRef echidnaTests
pure (vm, world, dict)
pure (vm, env, dict)

loadInitialCorpus :: Env -> World -> IO [(FilePath, [Tx])]
loadInitialCorpus env world = do
loadInitialCorpus :: Env -> IO [(FilePath, [Tx])]
loadInitialCorpus env = do
-- load transactions from init sequence (if any)
let sigs = Set.fromList $ concatMap NE.toList (Map.elems world.highSignatureMap)
let sigs = Set.fromList $ concatMap NE.toList (Map.elems env.world.highSignatureMap)
ethenoCorpus <-
case env.cfg.solConf.initialize of
Nothing -> pure []
Expand All @@ -112,18 +113,19 @@ loadInitialCorpus env world = do

pure $ persistedCorpus ++ ethenoCorpus

mkEnv :: EConfig -> BuildOutput -> IO Env
mkEnv cfg buildOutput = do
fetchContractCache <- newIORef mempty
fetchSlotCache <- newIORef mempty
mkEnv :: EConfig -> BuildOutput -> [EchidnaTest] -> World -> IO Env
mkEnv cfg buildOutput tests world = do
codehashMap <- newIORef mempty
chainId <- maybe (pure Nothing) EVM.Fetch.fetchChainIdFrom cfg.rpcUrl
eventQueue <- newChan
coverageRef <- newIORef mempty
corpusRef <- newIORef mempty
testsRef <- newIORef mempty
testRefs <- traverse newIORef tests
(contractCache, slotCache) <- Onchain.loadRpcCache cfg
fetchContractCache <- newIORef contractCache
fetchSlotCache <- newIORef slotCache
-- TODO put in real path
let dapp = dappInfo "/" buildOutput
pure $ Env { cfg, dapp, codehashMap, fetchContractCache, fetchSlotCache
, chainId, eventQueue, coverageRef, corpusRef, testsRef
, chainId, eventQueue, coverageRef, corpusRef, testRefs, world
}
2 changes: 1 addition & 1 deletion lib/Echidna/ABI.hs
Original file line number Diff line number Diff line change
Expand Up @@ -211,7 +211,7 @@ addChars c b = foldM withR b . enumFromTo 0 =<< rand where
addNulls :: MonadRandom m => ByteString -> m ByteString
addNulls = addChars $ pure 0

-- | Given a \"list-y\" structure with analogues of 'take', 'drop', and 'length',
-- | Given a \"list-y\" structure with analogs of 'take', 'drop', and 'length',
-- remove some elements at random.
shrinkWith
:: MonadRandom m
Expand Down
Loading

0 comments on commit e64a2a9

Please sign in to comment.