|
|
|
@ -1,21 +1,19 @@ |
|
|
|
|
{-# LANGUAGE DeriveGeneric, FlexibleContexts, TemplateHaskell #-} |
|
|
|
|
{-# LANGUAGE FlexibleContexts, TemplateHaskell #-} |
|
|
|
|
|
|
|
|
|
module Echidna.Config where |
|
|
|
|
|
|
|
|
|
import Control.Monad.Catch (MonadThrow(..)) |
|
|
|
|
import Control.Monad.IO.Class (MonadIO(..)) |
|
|
|
|
import Control.Monad.Reader (ReaderT, runReaderT) |
|
|
|
|
import Control.Lens |
|
|
|
|
import Control.Exception (Exception) |
|
|
|
|
import Control.Monad.Reader (ReaderT, runReaderT) |
|
|
|
|
import Data.Aeson |
|
|
|
|
import GHC.Generics |
|
|
|
|
|
|
|
|
|
import qualified Data.ByteString.Char8 as BS |
|
|
|
|
import qualified Data.Yaml as Y |
|
|
|
|
|
|
|
|
|
import EVM.Types (Addr, W256) |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
data Config = Config |
|
|
|
|
{ _solcArgs :: Maybe String |
|
|
|
|
, _epochs :: Int |
|
|
|
@ -25,50 +23,38 @@ data Config = Config |
|
|
|
|
, _contractAddr :: Addr |
|
|
|
|
, _sender :: Addr |
|
|
|
|
, _addrList :: Maybe [Addr] } |
|
|
|
|
deriving (Show, Generic) |
|
|
|
|
deriving Show |
|
|
|
|
|
|
|
|
|
makeLenses ''Config |
|
|
|
|
|
|
|
|
|
instance FromJSON Config |
|
|
|
|
instance FromJSON Config where |
|
|
|
|
parseJSON (Object v) = Config <$> v .:? "solcArgs" .!= Nothing |
|
|
|
|
<*> v .:? "epochs" .!= 2 |
|
|
|
|
<*> v .:? "testLimit" .!= 10000 |
|
|
|
|
<*> v .:? "range" .!= 10 |
|
|
|
|
<*> v .:? "gasLimit" .!= 0xffffffffffffffff |
|
|
|
|
<*> v .:? "contractAddr" .!= 0x00a329c0648769a73afac7f9381e08fb43dbea72 |
|
|
|
|
<*> v .:? "sender" .!= 0x00a329c0648769a73afac7f9381e08fb43dbea70 |
|
|
|
|
<*> v .:? "addrList" . .!= Nothing |
|
|
|
|
parseJSON _ = parseJSON (Object mempty) |
|
|
|
|
|
|
|
|
|
------------------------------------ |
|
|
|
|
-- Defaults |
|
|
|
|
|
|
|
|
|
defaultContractAddr :: Addr |
|
|
|
|
defaultContractAddr = 0x00a329c0648769a73afac7f9381e08fb43dbea72 |
|
|
|
|
|
|
|
|
|
defaultSender :: Addr |
|
|
|
|
defaultSender = 0x00a329c0648769a73afac7f9381e08fb43dbea70 |
|
|
|
|
newtype ParseException = ParseException FilePath |
|
|
|
|
|
|
|
|
|
defaultConfig :: Config |
|
|
|
|
defaultConfig = Config |
|
|
|
|
{ _solcArgs = Nothing |
|
|
|
|
, _epochs = 2 |
|
|
|
|
, _testLimit = 10000 |
|
|
|
|
, _range = 10 |
|
|
|
|
, _gasLimit = 0xffffffffffffffff |
|
|
|
|
, _contractAddr = defaultContractAddr |
|
|
|
|
, _sender = defaultSender |
|
|
|
|
, _addrList = Nothing } |
|
|
|
|
|
|
|
|
|
withDefaultConfig :: ReaderT Config m a -> m a |
|
|
|
|
withDefaultConfig = (flip runReaderT) defaultConfig |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
------------------------------------ |
|
|
|
|
-- Parser |
|
|
|
|
|
|
|
|
|
data ParseException = ParseException FilePath |
|
|
|
|
defaultConfig = either (error "Config parser got messed up :(") id $ Y.decodeEither "" |
|
|
|
|
|
|
|
|
|
instance Show ParseException where |
|
|
|
|
show (ParseException f) = "Could not parse config file " ++ (show f) |
|
|
|
|
show (ParseException f) = "Could not parse config file " ++ show f |
|
|
|
|
|
|
|
|
|
instance Exception ParseException |
|
|
|
|
|
|
|
|
|
parseConfig :: (MonadThrow m, MonadIO m) => FilePath -> m Config |
|
|
|
|
parseConfig file = do |
|
|
|
|
content <- liftIO $ BS.readFile file |
|
|
|
|
let parsedContent = Y.decode content :: Maybe Config |
|
|
|
|
case parsedContent of |
|
|
|
|
Nothing -> throwM (ParseException file) |
|
|
|
|
(Just c) -> return c |
|
|
|
|
content <- liftIO $ BS.readFile file |
|
|
|
|
let parsedContent = Y.decode content :: Maybe Config |
|
|
|
|
case parsedContent of |
|
|
|
|
Nothing -> throwM (ParseException file) |
|
|
|
|
(Just c) -> return c |
|
|
|
|
|
|
|
|
|
withDefaultConfig :: ReaderT Config m a -> m a |
|
|
|
|
withDefaultConfig = (`runReaderT` defaultConfig) |