@@ -5,7 +5,7 @@ import Data.Char (toLower)
55import Data.Foldable (toList )
66import Data.Function (on )
77import Data.Functor.Fixedpoint (Fix (.. ))
8- import Data.List (sortBy )
8+ import Data.List (nubBy , sortBy )
99import Data.List.Split (chunksOf )
1010import Data.Maybe (fromMaybe )
1111import qualified Data.Map as Map
@@ -47,7 +47,14 @@ sortJetName = sortBy (compare `on` name)
4747 where
4848 name (SomeArrow j) = jetName j
4949
50- cJetName = lowerSnakeCase . jetName
50+ rustJetName :: JetData x y -> String
51+ rustJetName jd = lowerSnakeCase (jetName jd)
52+
53+ cJetName :: JetData x y -> String
54+ cJetName jd = prefix (jetModule jd) ++ lowerSnakeCase (jetName jd)
55+ where
56+ prefix BitcoinModule = " bitcoin_"
57+ prefix _ = " "
5158
5259coreJetData :: (TyC x , TyC y ) => CoreJet x y -> JetData x y
5360coreJetData jet = JetData { jetName = mkName jet
@@ -88,6 +95,7 @@ moduleJets = sortJetName . toList . moduleCodes
8895
8996rustModuleName = fromMaybe " Core" . moduleName
9097lowerRustModuleName = map toLower . rustModuleName
98+ moduleEnvType mod = lowerRustModuleName mod ++ " ::CTxEnv, "
9199
92100coreModule :: Module
93101coreModule = Module Nothing (someArrowMap coreJetData <$> (treeEvalBitStream Core. getJetBit))
@@ -101,6 +109,11 @@ elementsModule = Module (Just "Elements") (someArrowMap elementsJetData <$> take
101109bitcoinModule :: Module
102110bitcoinModule = Module (Just " Bitcoin" ) (someArrowMap bitcoinJetData <$> takeRight (treeEvalBitStream Bitcoin. getJetBit))
103111
112+ allJets :: [SomeArrow JetData ]
113+ allJets = nubBy eqJet . sortJetName $ moduleJets =<< [bitcoinModule, elementsModule]
114+ where
115+ eqJet (SomeArrow jt1) (SomeArrow jt2) = jetName jt1 == jetName jt2 && jetModule jt1 == jetModule jt2
116+
104117data CompactTy = CTyOne
105118 | CTyWord Int
106119 | CTyMaybe CompactTy
@@ -191,16 +204,14 @@ rustJetTargetTy = rustJetTy "target_ty" (\(SomeArrow jet) -> unreflect (snd (rei
191204rustJetPtr :: Module -> Doc a
192205rustJetPtr mod = vsep $
193206 [ nest 4 (vsep (" fn c_jet_ptr(&self) -> &dyn Fn(&mut CFrameItem, CFrameItem, &Self::CJetEnvironment) -> bool {" :
194- if modname == " Bitcoin"
195- then [" unimplemented!(\" Bitcoin jets have not yet been implemented.\" )" ]
196- else [ nest 4 (vsep (" match self {" :
197- map (<> comma)
198- [ pretty modname <> " ::" <> pretty (jetName jet) <+> " =>" <+>
199- pretty (" &simplicity_sys::c_jets::jets_wrapper::" ++ cJetName jet)
200- | SomeArrow jet <- moduleJets mod
201- ]))
202- , " }"
203- ]))
207+ [ nest 4 (vsep (" match self {" :
208+ map (<> comma)
209+ [ pretty modname <> " ::" <> pretty (jetName jet) <+> " =>" <+>
210+ pretty (" &simplicity_sys::c_jets::jets_wrapper::" ++ cJetName jet)
211+ | SomeArrow jet <- moduleJets mod
212+ ]))
213+ , " }"
214+ ]))
204215 , " }"
205216 ]
206217 where
@@ -265,23 +276,26 @@ rustJetImpl mod = vsep $
265276 where
266277 modname = rustModuleName mod
267278 env = vsep
268- [ pretty $ " type Environment = " ++ env++ " ;"
279+ [ pretty $ " type Transaction = " ++ transaction++ " ;"
280+ , pretty $ " type Environment<T> = " ++ env++ " <T> where T: Borrow<Self::Transaction>;"
269281 , pretty $ " type CJetEnvironment = " ++ cEnv++ " ;"
270282 , " "
271- , pretty $ " fn c_jet_env(" ++ envArg++ " : &Self::Environment) -> &Self::CJetEnvironment {"
283+ , pretty $ " fn c_jet_env<T>(" ++ envArg++ " : &Self::Environment<T>) -> &Self::CJetEnvironment"
284+ , " where T: Borrow<Self::Transaction>"
285+ , " {"
272286 , pretty $ " " ++ envBody
273287 , " }"
274288 ]
275289 where
276- env | Nothing <- moduleName mod = " ()"
277- | Just " Elements" == moduleName mod = " ElementsEnv<std::sync::Arc<elements::Transaction>>"
290+ transaction | Nothing <- moduleName mod = " core::convert::Infallible"
291+ | Just name <- moduleName mod = map toLower name ++ " ::Transaction"
292+ env | Nothing <- moduleName mod = " CoreEnv"
278293 | Just name <- moduleName mod = name ++ " Env"
279- cEnv | Just " Elements " == moduleName mod = " CElementsTxEnv "
280- | otherwise = " () "
281- envArg | Just " Bitcoin " == moduleName mod = " _env "
294+ cEnv | Nothing <- moduleName mod = " CoreEnv<Self::Transaction> "
295+ | otherwise = " CTxEnv "
296+ envArg | Nothing <- moduleName mod = " _ "
282297 | otherwise = " env"
283- envBody | Nothing == moduleName mod = " env"
284- | Just " Bitcoin" == moduleName mod = " unimplemented!(\" Unspecified CJetEnvironment for Bitcoin jets\" )"
298+ envBody | Nothing <- moduleName mod = " &CoreEnv::EMPTY"
285299 | otherwise = " env.c_tx_env()"
286300
287301rustJetEnum :: Module -> Doc a
@@ -311,7 +325,7 @@ rustJetDisplay mod =
311325 nestBraces (" match self" <+>
312326 nestBraces (vsep (
313327 map (<> comma)
314- [ pretty modname <> " ::" <> pretty (jetName jet) <+> " => f.write_str" <> (parens . dquotes . pretty $ cJetName jet)
328+ [ pretty modname <> " ::" <> pretty (jetName jet) <+> " => f.write_str" <> (parens . dquotes . pretty $ rustJetName jet)
315329 | SomeArrow jet <- moduleJets mod
316330 ]))
317331 )
@@ -329,7 +343,7 @@ rustJetFromStr mod =
329343 nestBraces (" match s" <+>
330344 nestBraces (vsep (
331345 map (<> comma)
332- ([ dquotes (pretty (cJetName jet)) <+> " => Ok" <> parens (pretty modname <> " ::" <> pretty (jetName jet))
346+ ([ dquotes (pretty (rustJetName jet)) <+> " => Ok" <> parens (pretty modname <> " ::" <> pretty (jetName jet))
333347 | SomeArrow jet <- moduleJets mod
334348 ] ++ [ " x => Err(crate::Error::InvalidJetName(x.to_owned()))" ]
335349 )))
@@ -352,14 +366,13 @@ rustImports mod = vsep (map (<> semi)
352366 , " use hashes::sha256::Midstate"
353367 , " use simplicity_sys::CFrameItem"
354368 , " use std::io::Write"
355- , " use std::{fmt, str}"
369+ , " use std::{borrow::Borrow, fmt, str}"
356370 ] ++ envImports))
357371 where
358- envImports | Nothing == moduleName mod = []
359- | Just " Bitcoin" == moduleName mod = [" use crate::jet::bitcoin::BitcoinEnv" ]
372+ envImports | Nothing == moduleName mod = [" use crate::jet::core::CoreEnv" ]
360373 | Just name <- moduleName mod =
361374 [ pretty $ " use crate::jet::" ++ map toLower name++ " ::" ++ name++ " Env"
362- , pretty $ " use simplicity_sys::C " ++ name++ " TxEnv "
375+ , pretty $ " use simplicity_sys::" ++ map toLower name++ " ::CTxEnv "
363376 ]
364377
365378rustJetDoc :: Module -> SimpleDocStream a
@@ -375,14 +388,16 @@ rustJetDoc mod = layoutPretty layoutOptions $ vsep (map (<> line)
375388rustFFIImports :: Doc a
376389rustFFIImports = vsep (map (<> semi)
377390 [ " use crate::ffi::c_void"
378- , " use crate::{CElementsTxEnv, CFrameItem}"
391+ , " use crate::bitcoin"
392+ , " use crate::elements"
393+ , " use crate::CFrameItem"
379394 ])
380395
381- rustFFISigs :: Module -> Doc a
382- rustFFISigs mod = vsep
396+ rustFFISigs :: Doc a
397+ rustFFISigs = vsep
383398 [ nest 4 $ vsep $
384399 " extern \" C\" {" :
385- (declaration <$> moduleJets mod )
400+ (declaration <$> allJets )
386401 , " }"
387402 ]
388403 where
@@ -394,63 +409,68 @@ rustFFISigs mod = vsep
394409 linkName = " #[link_name = \" c_" ++ cJetName jet++ " \" ]"
395410 signature = " pub fn " ++ cJetName jet++ " (dst: *mut CFrameItem, src: *const CFrameItem, env: *const " ++ envType++ " ) -> bool"
396411 envType | CoreModule <- jetModule jet = " c_void"
397- | ElementsModule <- jetModule jet = " CElementsTxEnv"
412+ | ElementsModule <- jetModule jet = " elements::CTxEnv"
413+ | BitcoinModule <- jetModule jet = " bitcoin::CTxEnv"
398414
399- rustFFIDoc :: Module -> SimpleDocStream a
400- rustFFIDoc mod = layoutPretty layoutOptions $ vsep (map (<> line)
415+ rustFFIDoc :: SimpleDocStream a
416+ rustFFIDoc = layoutPretty layoutOptions $ vsep (map (<> line)
401417 [ rustHeader
402418 , rustFFIImports
403- , rustFFISigs mod
419+ , rustFFISigs
404420 ])
405421
406422rustWrapperImports :: Doc a
407423rustWrapperImports = vsep (map (<> semi)
408- [ " use crate::{CElementsTxEnv, CFrameItem}"
409- , " use super::elements_ffi"
424+ [ " use crate::bitcoin"
425+ , " use crate::elements"
426+ , " use crate::CFrameItem"
427+ , " use super::jets_ffi"
410428 ])
411429
412- rustWrappers :: Module -> Doc a
413- rustWrappers mod = vsep ((<> line) . wrapper <$> moduleJets mod )
430+ rustWrappers :: Doc a
431+ rustWrappers = vsep ((<> line) . wrapper <$> allJets )
414432 where
415433 wrapper (SomeArrow jet) = vsep
416434 [ nest 4 $ vsep
417435 [ pretty $ " pub fn " ++ cJetName jet++ templateParam++ " (dst: &mut CFrameItem, src: CFrameItem, " ++ envParam++ " ) -> bool {"
418- , pretty $ " unsafe { " ++ lowerRustModuleName mod ++ " _ffi ::" ++ cJetName jet++ " (dst, &src, " ++ envArg++ " ) }"
436+ , pretty $ " unsafe { jets_ffi ::" ++ cJetName jet++ " (dst, &src, " ++ envArg++ " ) }"
419437 ]
420438 , " }"
421439 ]
422440 where
423441 templateParam | CoreModule <- jetModule jet = " <T>"
424442 | otherwise = " "
425443 envParam | CoreModule <- jetModule jet = " _env: &T"
426- | ElementsModule <- jetModule jet = " env: &CElementsTxEnv"
444+ | ElementsModule <- jetModule jet = " env: &elements::CTxEnv"
445+ | BitcoinModule <- jetModule jet = " env: &bitcoin::CTxEnv"
427446 envArg | CoreModule <- jetModule jet = " std::ptr::null()"
428- | ElementsModule <- jetModule jet = " env"
447+ | otherwise = " env"
429448
430- rustWrapperDoc :: Module -> SimpleDocStream a
431- rustWrapperDoc mod = layoutPretty layoutOptions $ vsep (map (<> line)
449+ rustWrapperDoc :: SimpleDocStream a
450+ rustWrapperDoc = layoutPretty layoutOptions $ vsep (map (<> line)
432451 [ rustHeader
433452 , rustWrapperImports
434- , rustWrappers mod
453+ , rustWrappers
435454 ])
436455
437456cWrapperImports :: Doc a
438457cWrapperImports = vsep
439- [ " #include \" simplicity/elements/elementsJets.h\" "
458+ [ " #include \" simplicity/bitcoin/bitcoinJets.h\" "
459+ , " #include \" simplicity/elements/elementsJets.h\" "
440460 , " #include \" simplicity/simplicity_assert.h\" "
441461 , " #include \" wrapper.h\" "
442462 ]
443463
444- cWrappers :: Module -> Doc a
445- cWrappers mod = vsep (map wrapper $ moduleJets mod )
464+ cWrappers :: Doc a
465+ cWrappers = vsep (map wrapper $ allJets )
446466 where
447467 wrapper (SomeArrow jet) = pretty $ " WRAP_(" ++ cJetName jet++ " )"
448468
449- cWrapperDoc :: Module -> SimpleDocStream a
450- cWrapperDoc mod = layoutPretty layoutOptions $ vsep (map (<> line)
469+ cWrapperDoc :: SimpleDocStream a
470+ cWrapperDoc = layoutPretty layoutOptions $ vsep (map (<> line)
451471 [ rustHeader -- also works for C
452472 , cWrapperImports
453- , cWrappers mod
473+ , cWrappers
454474 ])
455475
456476renderFile name doc = withFile name WriteMode (\ h -> renderIO h doc)
@@ -459,8 +479,8 @@ main = do
459479 renderFile " core.rs" (rustJetDoc coreModule)
460480 renderFile " elements.rs" (rustJetDoc elementsModule)
461481 renderFile " bitcoin.rs" (rustJetDoc bitcoinModule)
462- renderFile " jets_ffi.rs" ( rustFFIDoc elementsModule)
463- renderFile " jets_wrapper.rs" ( rustWrapperDoc elementsModule)
464- renderFile " jets_wrapper.c" ( cWrapperDoc elementsModule)
482+ renderFile " jets_ffi.rs" rustFFIDoc
483+ renderFile " jets_wrapper.rs" rustWrapperDoc
484+ renderFile " jets_wrapper.c" cWrapperDoc
465485
466486layoutOptions = LayoutOptions { layoutPageWidth = AvailablePerLine 100 1 }
0 commit comments