@@ -68,7 +68,7 @@ state type crate_ctxt = rec(session.session sess,
68
68
hashmap[ ast. def_id , ValueRef ] item_ids,
69
69
hashmap[ ast. def_id , @ast. item ] items,
70
70
hashmap[ ast. def_id , @tag_info] tags,
71
- hashmap[ @typeck. ty , @ty_info ] types ,
71
+ hashmap[ @typeck. ty , ValueRef ] tydescs ,
72
72
@glue_fns glues,
73
73
namegen names,
74
74
str path) ;
@@ -471,19 +471,6 @@ fn C_struct(vec[ValueRef] elts) -> ValueRef {
471
471
False ) ;
472
472
}
473
473
474
- fn C_tydesc ( TypeRef t) -> ValueRef {
475
- ret C_struct ( vec ( C_null ( T_ptr ( T_opaque ( ) ) ) , // first_param
476
- llvm. LLVMSizeOf ( t) , // size
477
- llvm. LLVMAlignOf ( t) , // align
478
- C_null ( T_ptr ( T_opaque ( ) ) ) , // copy_glue_off
479
- C_null ( T_ptr ( T_opaque ( ) ) ) , // drop_glue_off
480
- C_null ( T_ptr ( T_opaque ( ) ) ) , // free_glue_off
481
- C_null ( T_ptr ( T_opaque ( ) ) ) , // sever_glue_off
482
- C_null ( T_ptr ( T_opaque ( ) ) ) , // mark_glue_off
483
- C_null ( T_ptr ( T_opaque ( ) ) ) , // obj_drop_glue_off
484
- C_null ( T_ptr ( T_opaque ( ) ) ) ) ) ; // is_stateful
485
- }
486
-
487
474
fn decl_fn ( ModuleRef llmod, str name , uint cc, TypeRef llty) -> ValueRef {
488
475
let ValueRef llfn =
489
476
llvm. LLVMAddFunction ( llmod, _str. buf ( name) , llty) ;
@@ -576,21 +563,48 @@ fn trans_malloc(@block_ctxt cx, @typeck.ty t) -> result {
576
563
}
577
564
578
565
579
- // Glue and referent count twiddling
566
+ // Type descriptor and type glue stuff
567
+
568
+ // Given a type and a field index into its corresponding type descriptor,
569
+ // returns an LLVM ValueRef of that field from the tydesc, generating the
570
+ // tydesc if necessary.
571
+ fn field_of_tydesc ( @block_ctxt cx , @typeck . ty ty, int field ) -> ValueRef {
572
+ auto tydesc = get_tydesc ( cx. fcx . ccx , ty) ;
573
+ ret cx. build . GEP ( tydesc, vec ( C_int ( 0 ) , C_int ( field) ) ) ;
574
+ }
580
575
581
- fn get_ty_info ( @crate_ctxt cx , @typeck . ty ty) -> @ ty_info {
582
- if ( !cx. types . contains_key ( ty) ) {
583
- make_ty_info ( cx, ty) ;
576
+ fn get_tydesc ( @crate_ctxt cx , @typeck . ty ty) -> ValueRef {
577
+ if ( !cx. tydescs . contains_key ( ty) ) {
578
+ make_tydesc ( cx, ty) ;
584
579
}
585
- ret cx. types . get ( ty) ;
580
+ ret cx. tydescs . get ( ty) ;
586
581
}
587
582
588
- fn make_ty_info ( @crate_ctxt cx , @typeck . ty ty) {
583
+ fn make_tydesc ( @crate_ctxt cx , @typeck . ty ty) {
589
584
auto tg = make_take_glue;
590
585
auto take_glue = make_generic_glue ( cx, ty, "take" , tg) ;
591
586
auto dg = make_drop_glue;
592
587
auto drop_glue = make_generic_glue ( cx, ty, "drop" , dg) ;
593
- cx. types . insert ( ty, @rec ( take_glue=take_glue, drop_glue=drop_glue) ) ;
588
+
589
+ auto llty = type_of ( cx, ty) ;
590
+ auto pvoid = T_ptr ( T_i8 ( ) ) ;
591
+ auto glue_fn_ty = T_ptr ( T_fn ( vec ( T_taskptr ( ) , pvoid) , T_void ( ) ) ) ;
592
+ auto tydesc = C_struct ( vec ( C_null ( pvoid) ,
593
+ llvm. LLVMSizeOf ( llty) ,
594
+ llvm. LLVMAlignOf ( llty) ,
595
+ take_glue, // copy_glue_off
596
+ drop_glue, // drop_glue_off
597
+ C_null ( glue_fn_ty) , // free_glue_off
598
+ C_null ( glue_fn_ty) , // sever_glue_off
599
+ C_null ( glue_fn_ty) , // mark_glue_off
600
+ C_null ( glue_fn_ty) , // obj_drop_glue_off
601
+ C_null ( glue_fn_ty) ) ) ; // is_stateful
602
+
603
+ auto name = sanitize ( cx. names . next ( "tydesc_" + typeck. ty_to_str ( ty) ) ) ;
604
+ auto gvar = llvm. LLVMAddGlobal ( cx. llmod , val_ty ( tydesc) , _str. buf ( name) ) ;
605
+ llvm. LLVMSetInitializer ( gvar, tydesc) ;
606
+ llvm. LLVMSetGlobalConstant ( gvar, True ) ;
607
+ cx. tydescs . insert ( ty, gvar) ;
594
608
}
595
609
596
610
fn make_generic_glue ( @crate_ctxt cx , @typeck. ty t , str name ,
@@ -970,8 +984,9 @@ fn incr_all_refcnts(@block_ctxt cx,
970
984
@typeck. ty t) -> result {
971
985
if ( !typeck. type_is_scalar( t) ) {
972
986
auto llrawptr = cx. build. BitCast ( v, T_ptr ( T_i8 ( ) ) ) ;
973
- cx. build. FastCall ( get_ty_info( cx. fcx. ccx, t) . take_glue,
974
- vec( cx. fcx. lltaskptr, llrawptr) ) ;
987
+ auto llfnptr = field_of_tydesc( cx, t, abi. tydesc_field_copy_glue_off) ;
988
+ auto llfn = cx. build. Load ( llfnptr) ;
989
+ cx. build. FastCall ( llfn, vec( cx. fcx. lltaskptr, llrawptr) ) ;
975
990
}
976
991
ret res( cx, C_nil ( ) ) ;
977
992
}
@@ -993,8 +1008,9 @@ fn drop_ty(@block_ctxt cx,
993
1008
@typeck. ty t) -> result {
994
1009
if ( !typeck. type_is_scalar( t) ) {
995
1010
auto llrawptr = cx. build. BitCast ( v, T_ptr ( T_i8 ( ) ) ) ;
996
- cx. build. FastCall ( get_ty_info( cx. fcx. ccx, t) . drop_glue,
997
- vec( cx. fcx. lltaskptr, llrawptr) ) ;
1011
+ auto llfnptr = field_of_tydesc( cx, t, abi. tydesc_field_drop_glue_off) ;
1012
+ auto llfn = cx. build. Load ( llfnptr) ;
1013
+ cx. build. FastCall ( llfn, vec( cx. fcx. lltaskptr, llrawptr) ) ;
998
1014
}
999
1015
ret res( cx, C_nil ( ) ) ;
1000
1016
}
@@ -2833,7 +2849,7 @@ fn trans_crate(session.session sess, @ast.crate crate, str output) {
2833
2849
auto glues = make_glues ( llmod) ;
2834
2850
auto hasher = typeck. hash_ty ;
2835
2851
auto eqer = typeck. eq_ty ;
2836
- auto types = map. mk_hashmap [ @typeck. ty , @ty_info ] ( hasher, eqer) ;
2852
+ auto tydescs = map. mk_hashmap [ @typeck. ty , ValueRef ] ( hasher, eqer) ;
2837
2853
2838
2854
auto cx = @rec ( sess = sess,
2839
2855
llmod = llmod,
@@ -2844,7 +2860,7 @@ fn trans_crate(session.session sess, @ast.crate crate, str output) {
2844
2860
item_ids = new_def_hash[ ValueRef ] ( ) ,
2845
2861
items = new_def_hash[ @ast. item ] ( ) ,
2846
2862
tags = new_def_hash[ @tag_info] ( ) ,
2847
- types = types ,
2863
+ tydescs = tydescs ,
2848
2864
glues = glues,
2849
2865
names = namegen ( 0 ) ,
2850
2866
path = "_rust" ) ;
0 commit comments