@@ -18,35 +18,39 @@ import Cardano.Api
18
18
import Cardano.Benchmarking.Types
19
19
import Cardano.Benchmarking.NixOptions
20
20
import Cardano.Benchmarking.Script.Setters
21
- import Cardano.Benchmarking.Script.Store (Name (.. ))
21
+ import Cardano.Benchmarking.Script.Store (Name (.. ), WalletName )
22
22
import Cardano.Benchmarking.Script.Types
23
23
24
24
data CompileError where
25
25
SomeCompilerError :: CompileError
26
26
deriving (Show )
27
- type Compiler a = RWST NixServiceOptions (DList Action ) () (Except CompileError ) a
27
+ type Compiler a = RWST NixServiceOptions (DList Action ) Int (Except CompileError ) a
28
+
29
+ type SrcWallet = WalletName
30
+ type DstWallet = WalletName
28
31
29
32
compileOptions :: NixServiceOptions -> Either CompileError [Action ]
30
- compileOptions = runCompiler compileToScript
33
+ compileOptions opts = runCompiler opts compileToScript
31
34
32
- runCompiler :: Compiler () -> NixServiceOptions -> Either CompileError [Action ]
33
- runCompiler c o = case runExcept $ runRWST c o () of
35
+ runCompiler :: NixServiceOptions -> Compiler () -> Either CompileError [Action ]
36
+ runCompiler o c = case runExcept $ runRWST c o 0 of
34
37
Left err -> Left err
35
38
Right (() , _ , l) -> Right $ DL. toList l
36
39
37
- testCompiler :: Compiler a -> NixServiceOptions -> Either CompileError (a , () , [Action ])
38
- testCompiler c o = case runExcept $ runRWST c o () of
40
+ testCompiler :: NixServiceOptions -> Compiler a -> Either CompileError (a , Int , [Action ])
41
+ testCompiler o c = case runExcept $ runRWST c o 0 of
39
42
Left err -> Left err
40
43
Right (a, s , l) -> Right (a, s, DL. toList l)
41
44
42
45
compileToScript :: Compiler ()
43
46
compileToScript = do
44
47
initConstants
45
48
emit . StartProtocol =<< askNixOption _nix_nodeConfigFile
46
- importGenesisFunds
47
- initCollaterals
48
- splittingPhase
49
- benchmarkingPhase
49
+ genesisWallet <- newWallet " genesis_wallet"
50
+ importGenesisFunds genesisWallet
51
+ splitWallet <- splittingPhase genesisWallet
52
+ addCollaterals genesisWallet splitWallet
53
+ benchmarkingPhase splitWallet
50
54
51
55
initConstants :: Compiler ()
52
56
initConstants = do
@@ -67,61 +71,78 @@ initConstants = do
67
71
setN :: Tag v -> (NixServiceOptions -> v ) -> Compiler ()
68
72
setN key s = askNixOption s >>= setConst key
69
73
70
- importGenesisFunds :: Compiler ()
71
- importGenesisFunds = do
74
+ importGenesisFunds :: DstWallet -> Compiler ()
75
+ importGenesisFunds wallet = do
72
76
cmd1 (ReadSigningKey $ KeyName " pass-partout" ) _nix_sigKey
73
- emit $ ImportGenesisFund LocalSocket (KeyName " pass-partout" ) (KeyName " pass-partout" )
77
+ emit $ ImportGenesisFund wallet LocalSocket (KeyName " pass-partout" ) (KeyName " pass-partout" )
74
78
delay
75
79
76
- initCollaterals :: Compiler ()
77
- initCollaterals = do
80
+ addCollaterals :: SrcWallet -> DstWallet -> Compiler ()
81
+ addCollaterals src dest = do
78
82
isAnyPlutusMode >>= \ case
79
83
False -> return ()
80
84
True -> do
81
85
tx_fee <- askNixOption _nix_tx_fee
82
86
safeCollateral <- _safeCollateral <$> evilFeeMagic
83
- emit $ CreateChange LocalSocket (PayToAddr $ KeyName " pass-partout" ) (safeCollateral + tx_fee) 1
84
- emit $ CreateChange LocalSocket (PayToCollateral $ KeyName " pass-partout" ) safeCollateral 1
87
+ emit $ CreateChange src src LocalSocket (PayToAddr $ KeyName " pass-partout" ) (safeCollateral + tx_fee) 1
88
+ emit $ CreateChange src dest LocalSocket (PayToCollateral $ KeyName " pass-partout" ) safeCollateral 1
85
89
86
- splittingPhase :: Compiler ()
87
- splittingPhase = do
90
+ splittingPhase :: SrcWallet -> Compiler DstWallet
91
+ splittingPhase srcWallet = do
88
92
(NumberOfTxs tx_count) <- askNixOption _nix_tx_count
89
93
(NumberOfInputsPerTx inputs_per_tx) <- askNixOption _nix_inputs_per_tx
94
+ tx_fee <- askNixOption _nix_tx_fee
90
95
minValuePerInput <- _minValuePerInput <$> evilFeeMagic
96
+ splitSteps <- splitSequenceWalletNames srcWallet srcWallet $ unfoldSplitSequence tx_fee minValuePerInput (tx_count * inputs_per_tx)
97
+ forM_ (init splitSteps) createChange
91
98
plutus <- isAnyPlutusMode
92
- if plutus then createChangeRecursivePlutus minValuePerInput (tx_count * inputs_per_tx)
93
- else createChangeRecursive minValuePerInput (tx_count * inputs_per_tx)
99
+ (if plutus then createChangePlutus else createChange) $ last splitSteps
94
100
where
95
- createChangeRecursive :: Lovelace -> Int -> Compiler ()
96
- createChangeRecursive value count = do
97
- when (count > 30 ) $ do
98
- tx_fee <- askNixOption _nix_tx_fee
99
- createChangeRecursive (value * 30 + tx_fee) (count `div` 30 + 1 )
100
- createChange value count
101
-
102
- createChangeRecursivePlutus :: Lovelace -> Int -> Compiler ()
103
- createChangeRecursivePlutus value count = do
104
- when (count > 30 ) $ do
105
- tx_fee <- askNixOption _nix_tx_fee
106
- createChangeRecursive (value * 30 + tx_fee) (count `div` 30 + 1 )
107
- createChangePlutus value count
108
-
109
- createChange :: Lovelace -> Int -> Compiler ()
110
- createChange value count = do
111
- emit $ CreateChange LocalSocket (PayToAddr $ KeyName " pass-partout" ) value count
101
+ createChange :: SplitStep -> Compiler DstWallet
102
+ createChange (src, dst, value, count) = do
103
+ emit $ CreateChange src dst LocalSocket (PayToAddr $ KeyName " pass-partout" ) value count
112
104
delay
105
+ return dst
113
106
114
- createChangePlutus :: Lovelace -> Int -> Compiler ()
115
- createChangePlutus value count = do
107
+ createChangePlutus :: SplitStep -> Compiler DstWallet
108
+ createChangePlutus (src, dst, value, count) = do
116
109
autoMode <- isPlutusAutoMode
117
110
plutusTarget <- if autoMode
118
111
then PayToScript <$> askNixOption _nix_plutusLoopScript <*> pure (ScriptDataNumber 0 )
119
112
else PayToScript <$> askNixOption _nix_plutusScript <*> (ScriptDataNumber <$> askNixOption _nix_plutusData)
120
- emit $ CreateChange LocalSocket plutusTarget value count
113
+ emit $ CreateChange src dst LocalSocket plutusTarget value count
121
114
delay
122
-
123
- benchmarkingPhase :: Compiler ()
124
- benchmarkingPhase = do
115
+ return dst
116
+
117
+ -- Generate src and dst wallet names for a splitSequence.
118
+ -- testCompiler (error "opts") $ splitSequenceWalletNames (WalletName "w1") (WalletName "w2") (unfoldSplitSequence 1 1000 10000)
119
+ type SplitStep = (SrcWallet , DstWallet , Lovelace , Int )
120
+
121
+ splitSequenceWalletNames :: SrcWallet -> DstWallet -> [(Lovelace , Int )] -> Compiler [ SplitStep ]
122
+ splitSequenceWalletNames _src _dst [] = return []
123
+ splitSequenceWalletNames src dst [ (val,count) ] = return [( src, dst, val, count)]
124
+ splitSequenceWalletNames src dst ((val, count): rest) = do
125
+ nextDst <- newWallet " change_wallet"
126
+ l <- splitSequenceWalletNames dst nextDst rest
127
+ return $ [( src, dst, val, count)] ++ l
128
+
129
+ -- Return a list of splitSteps.
130
+ unfoldSplitSequence :: Lovelace -> Lovelace -> Int -> [(Lovelace , Int )]
131
+ unfoldSplitSequence fee value count
132
+ = if count < maxOutputs
133
+ then [
134
+ -- Add an extra transaction that just contains the desired output and possible fees.
135
+ (value * fromIntegral count + fee, 1 )
136
+ , (value, count )
137
+ ]
138
+ else unfoldSplitSequence fee (value * fromIntegral maxOutputs + fee) (count `div` maxOutputs + 1 ) ++ [ (value, count) ]
139
+ where
140
+ -- maximal number of outputs in a TX.
141
+ -- todo: this must be in sync with Scipt/Core.hs
142
+ maxOutputs = 30
143
+
144
+ benchmarkingPhase :: WalletName -> Compiler ()
145
+ benchmarkingPhase wallet = do
125
146
debugMode <- askNixOption _nix_debugMode
126
147
plutusMode <- askNixOption _nix_plutusMode
127
148
plutusAutoMode <- askNixOption _nix_plutusAutoMode
@@ -140,7 +161,7 @@ benchmarkingPhase = do
140
161
<*> (ScriptDataNumber <$> askNixOption _nix_plutusData)
141
162
<*> (ScriptDataNumber <$> askNixOption _nix_plutusRedeemer)
142
163
(False ,False ) -> return SpendOutput
143
- emit $ RunBenchmark target spendMode (ThreadName " tx-submit-benchmark" ) tx_count tps
164
+ emit $ RunBenchmark wallet target spendMode (ThreadName " tx-submit-benchmark" ) tx_count tps
144
165
unless debugMode $ do
145
166
emit $ WaitBenchmark $ ThreadName " tx-submit-benchmark"
146
167
@@ -191,3 +212,17 @@ isPlutusAutoMode = askNixOption _nix_plutusAutoMode
191
212
192
213
isAnyPlutusMode :: Compiler Bool
193
214
isAnyPlutusMode = liftA2 (||) isPlutusMode isPlutusAutoMode
215
+
216
+ newIdentifier :: String -> Compiler String
217
+ newIdentifier prefix = do
218
+ n <- get
219
+ put $ succ n
220
+ return $ prefix ++ " _" ++ show n
221
+
222
+ newWallet :: String -> Compiler WalletName
223
+ newWallet n = do
224
+ name <- WalletName <$> newIdentifier n
225
+ emit $ InitWallet name
226
+ return name
227
+
228
+
0 commit comments