@@ -26,6 +26,7 @@ use middle::lang_items::LangItem;
26
26
use middle:: subst:: { self , Substs } ;
27
27
use trans:: base;
28
28
use trans:: build;
29
+ use trans:: builder:: Builder ;
29
30
use trans:: callee;
30
31
use trans:: cleanup;
31
32
use trans:: consts;
@@ -45,6 +46,7 @@ use util::nodemap::{FnvHashMap, NodeMap};
45
46
46
47
use arena:: TypedArena ;
47
48
use libc:: { c_uint, c_char} ;
49
+ use std:: ops:: Deref ;
48
50
use std:: ffi:: CString ;
49
51
use std:: cell:: { Cell , RefCell } ;
50
52
use std:: vec:: Vec ;
@@ -613,6 +615,9 @@ impl<'blk, 'tcx> BlockS<'blk, 'tcx> {
613
615
pub fn ccx ( & self ) -> & ' blk CrateContext < ' blk , ' tcx > {
614
616
self . fcx . ccx
615
617
}
618
+ pub fn fcx ( & self ) -> & ' blk FunctionContext < ' blk , ' tcx > {
619
+ self . fcx
620
+ }
616
621
pub fn tcx ( & self ) -> & ' blk ty:: ctxt < ' tcx > {
617
622
self . fcx . ccx . tcx ( )
618
623
}
@@ -659,6 +664,109 @@ impl<'blk, 'tcx> BlockS<'blk, 'tcx> {
659
664
self . fcx . param_substs ,
660
665
value)
661
666
}
667
+
668
+ pub fn build ( & ' blk self ) -> BlockAndBuilder < ' blk , ' tcx > {
669
+ BlockAndBuilder :: new ( self , OwnedBuilder :: new_with_ccx ( self . ccx ( ) ) )
670
+ }
671
+ }
672
+
673
+ pub struct OwnedBuilder < ' blk , ' tcx : ' blk > {
674
+ builder : Builder < ' blk , ' tcx >
675
+ }
676
+
677
+ impl < ' blk , ' tcx > OwnedBuilder < ' blk , ' tcx > {
678
+ pub fn new_with_ccx ( ccx : & ' blk CrateContext < ' blk , ' tcx > ) -> Self {
679
+ // Create a fresh builder from the crate context.
680
+ let llbuilder = unsafe {
681
+ llvm:: LLVMCreateBuilderInContext ( ccx. llcx ( ) )
682
+ } ;
683
+ OwnedBuilder {
684
+ builder : Builder {
685
+ llbuilder : llbuilder,
686
+ ccx : ccx,
687
+ }
688
+ }
689
+ }
690
+ }
691
+
692
+ impl < ' blk , ' tcx > Drop for OwnedBuilder < ' blk , ' tcx > {
693
+ fn drop ( & mut self ) {
694
+ unsafe {
695
+ llvm:: LLVMDisposeBuilder ( self . builder . llbuilder ) ;
696
+ }
697
+ }
698
+ }
699
+
700
+ pub struct BlockAndBuilder < ' blk , ' tcx : ' blk > {
701
+ bcx : Block < ' blk , ' tcx > ,
702
+ owned_builder : OwnedBuilder < ' blk , ' tcx > ,
703
+ }
704
+
705
+ impl < ' blk , ' tcx > BlockAndBuilder < ' blk , ' tcx > {
706
+ pub fn new ( bcx : Block < ' blk , ' tcx > , owned_builder : OwnedBuilder < ' blk , ' tcx > ) -> Self {
707
+ // Set the builder's position to this block's end.
708
+ owned_builder. builder . position_at_end ( bcx. llbb ) ;
709
+ BlockAndBuilder {
710
+ bcx : bcx,
711
+ owned_builder : owned_builder,
712
+ }
713
+ }
714
+
715
+ pub fn with_block < F , R > ( & self , f : F ) -> R
716
+ where F : FnOnce ( Block < ' blk , ' tcx > ) -> R
717
+ {
718
+ let result = f ( self . bcx ) ;
719
+ self . position_at_end ( self . bcx . llbb ) ;
720
+ result
721
+ }
722
+
723
+ pub fn map_block < F > ( self , f : F ) -> Self
724
+ where F : FnOnce ( Block < ' blk , ' tcx > ) -> Block < ' blk , ' tcx >
725
+ {
726
+ let BlockAndBuilder { bcx, owned_builder } = self ;
727
+ let bcx = f ( bcx) ;
728
+ BlockAndBuilder :: new ( bcx, owned_builder)
729
+ }
730
+
731
+ // Methods delegated to bcx
732
+
733
+ pub fn ccx ( & self ) -> & ' blk CrateContext < ' blk , ' tcx > {
734
+ self . bcx . ccx ( )
735
+ }
736
+ pub fn fcx ( & self ) -> & ' blk FunctionContext < ' blk , ' tcx > {
737
+ self . bcx . fcx ( )
738
+ }
739
+ pub fn tcx ( & self ) -> & ' blk ty:: ctxt < ' tcx > {
740
+ self . bcx . tcx ( )
741
+ }
742
+ pub fn sess ( & self ) -> & ' blk Session {
743
+ self . bcx . sess ( )
744
+ }
745
+
746
+ pub fn llbb ( & self ) -> BasicBlockRef {
747
+ self . bcx . llbb
748
+ }
749
+
750
+ pub fn mir ( & self ) -> & ' blk Mir < ' tcx > {
751
+ self . bcx . mir ( )
752
+ }
753
+
754
+ pub fn val_to_string ( & self , val : ValueRef ) -> String {
755
+ self . bcx . val_to_string ( val)
756
+ }
757
+
758
+ pub fn monomorphize < T > ( & self , value : & T ) -> T
759
+ where T : TypeFoldable < ' tcx >
760
+ {
761
+ self . bcx . monomorphize ( value)
762
+ }
763
+ }
764
+
765
+ impl < ' blk , ' tcx > Deref for BlockAndBuilder < ' blk , ' tcx > {
766
+ type Target = Builder < ' blk , ' tcx > ;
767
+ fn deref ( & self ) -> & Self :: Target {
768
+ & self . owned_builder . builder
769
+ }
662
770
}
663
771
664
772
/// A structure representing an active landing pad for the duration of a basic
0 commit comments