@@ -17,6 +17,7 @@ use e = metadata::encoder;
17
17
use metadata:: decoder;
18
18
use metadata:: encoder;
19
19
use metadata:: tydecode;
20
+ use metadata:: tydecode:: { DefIdSource , NominalType , TypeWithId , TypeParameter } ;
20
21
use metadata:: tyencode;
21
22
use middle:: freevars:: freevar_entry;
22
23
use middle:: typeck:: { method_origin, method_map_entry, vtable_res} ;
@@ -168,14 +169,55 @@ fn reserve_id_range(sess: Session,
168
169
169
170
impl extended_decode_ctxt {
170
171
fn tr_id ( id : ast:: node_id ) -> ast:: node_id {
172
+ /*!
173
+ *
174
+ * Translates an internal id, meaning a node id that is known
175
+ * to refer to some part of the item currently being inlined,
176
+ * such as a local variable or argument. All naked node-ids
177
+ * that appear in types have this property, since if something
178
+ * might refer to an external item we would use a def-id to
179
+ * allow for the possibility that the item resides in another
180
+ * crate.
181
+ */
182
+
171
183
// from_id_range should be non-empty
172
184
assert !ast_util:: empty ( self . from_id_range ) ;
173
185
( id - self . from_id_range . min + self . to_id_range . min )
174
186
}
175
187
fn tr_def_id ( did : ast:: def_id ) -> ast:: def_id {
188
+ /*!
189
+ *
190
+ * Translates an EXTERNAL def-id, converting the crate number
191
+ * from the one used in the encoded data to the current crate
192
+ * numbers.. By external, I mean that it be translated to a
193
+ * reference to the item in its original crate, as opposed to
194
+ * being translated to a reference to the inlined version of
195
+ * the item. This is typically, but not always, what you
196
+ * want, because most def-ids refer to external things like
197
+ * types or other fns that may or may not be inlined. Note
198
+ * that even when the inlined function is referencing itself
199
+ * recursively, we would want `tr_def_id` for that
200
+ * reference--- conceptually the function calls the original,
201
+ * non-inlined version, and trans deals with linking that
202
+ * recursive call to the inlined copy.
203
+ *
204
+ * However, there are a *few* cases where def-ids are used but
205
+ * we know that the thing being referenced is in fact *internal*
206
+ * to the item being inlined. In those cases, you should use
207
+ * `tr_intern_def_id()` below.
208
+ */
209
+
176
210
decoder:: translate_def_id ( self . dcx . cdata , did)
177
211
}
178
212
fn tr_intern_def_id ( did : ast:: def_id ) -> ast:: def_id {
213
+ /*!
214
+ *
215
+ * Translates an INTERNAL def-id, meaning a def-id that is
216
+ * known to refer to some part of the item currently being
217
+ * inlined. In that case, we want to convert the def-id to
218
+ * refer to the current crate and to the new, inlined node-id.
219
+ */
220
+
179
221
assert did. crate == ast:: local_crate;
180
222
ast:: def_id { crate : ast:: local_crate, node : self . tr_id ( did. node ) }
181
223
}
@@ -906,15 +948,17 @@ trait ebml_decoder_decoder_helpers {
906
948
fn read_bounds ( xcx : extended_decode_ctxt ) -> @~[ ty:: param_bound ] ;
907
949
fn read_ty_param_bounds_and_ty ( xcx : extended_decode_ctxt )
908
950
-> ty:: ty_param_bounds_and_ty ;
951
+ fn convert_def_id ( xcx : extended_decode_ctxt ,
952
+ source : DefIdSource ,
953
+ did : ast:: def_id ) -> ast:: def_id ;
909
954
}
910
955
911
956
impl reader:: Decoder : ebml_decoder_decoder_helpers {
912
-
913
957
fn read_arg ( xcx : extended_decode_ctxt ) -> ty:: arg {
914
958
do self . read_opaque |doc| {
915
959
tydecode:: parse_arg_data (
916
960
doc. data , xcx. dcx . cdata . cnum , doc. start , xcx. dcx . tcx ,
917
- |a| xcx . tr_def_id ( a) )
961
+ |s , a| self . convert_def_id ( xcx , s , a) )
918
962
}
919
963
}
920
964
@@ -927,7 +971,7 @@ impl reader::Decoder: ebml_decoder_decoder_helpers {
927
971
do self . read_opaque |doc| {
928
972
tydecode:: parse_ty_data (
929
973
doc. data , xcx. dcx . cdata . cnum , doc. start , xcx. dcx . tcx ,
930
- |a| xcx . tr_def_id ( a) )
974
+ |s , a| self . convert_def_id ( xcx , s , a) )
931
975
}
932
976
}
933
977
@@ -939,7 +983,7 @@ impl reader::Decoder: ebml_decoder_decoder_helpers {
939
983
do self . read_opaque |doc| {
940
984
tydecode:: parse_bounds_data (
941
985
doc. data , doc. start , xcx. dcx . cdata . cnum , xcx. dcx . tcx ,
942
- |a| xcx . tr_def_id ( a) )
986
+ |s , a| self . convert_def_id ( xcx , s , a) )
943
987
}
944
988
}
945
989
@@ -960,6 +1004,29 @@ impl reader::Decoder: ebml_decoder_decoder_helpers {
960
1004
}
961
1005
}
962
1006
}
1007
+
1008
+ fn convert_def_id ( xcx : extended_decode_ctxt ,
1009
+ source : tydecode:: DefIdSource ,
1010
+ did : ast:: def_id ) -> ast:: def_id {
1011
+ /*!
1012
+ *
1013
+ * Converts a def-id that appears in a type. The correct
1014
+ * translation will depend on what kind of def-id this is.
1015
+ * This is a subtle point: type definitions are not
1016
+ * inlined into the current crate, so if the def-id names
1017
+ * a nominal type or type alias, then it should be
1018
+ * translated to refer to the source crate.
1019
+ *
1020
+ * However, *type parameters* are cloned along with the function
1021
+ * they are attached to. So we should translate those def-ids
1022
+ * to refer to the new, cloned copy of the type parameter.
1023
+ */
1024
+
1025
+ match source {
1026
+ NominalType | TypeWithId => xcx. tr_def_id ( did) ,
1027
+ TypeParameter => xcx. tr_intern_def_id ( did)
1028
+ }
1029
+ }
963
1030
}
964
1031
965
1032
fn decode_side_tables ( xcx : extended_decode_ctxt ,
0 commit comments