@@ -1130,20 +1130,39 @@ fn report_assoc_ty_on_inherent_impl<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, span:
11301130}
11311131
11321132fn type_of < ' a , ' tcx > ( tcx : TyCtxt < ' a , ' tcx , ' tcx > , def_id : DefId ) -> Ty < ' tcx > {
1133+ checked_type_of ( tcx, def_id, true ) . unwrap ( )
1134+ }
1135+
1136+ pub fn checked_type_of < ' a , ' tcx > (
1137+ tcx : TyCtxt < ' a , ' tcx , ' tcx > ,
1138+ def_id : DefId ,
1139+ fail : bool ,
1140+ ) -> Option < Ty < ' tcx > > {
11331141 use rustc:: hir:: * ;
11341142
1135- let hir_id = tcx. hir ( ) . as_local_hir_id ( def_id) . unwrap ( ) ;
1143+ let hir_id = match tcx. hir ( ) . as_local_hir_id ( def_id) {
1144+ Some ( hir_id) => hir_id,
1145+ None => {
1146+ if !fail {
1147+ return None ;
1148+ }
1149+ bug ! ( "invalid node" ) ;
1150+ }
1151+ } ;
11361152
11371153 let icx = ItemCtxt :: new ( tcx, def_id) ;
11381154
1139- match tcx. hir ( ) . get_by_hir_id ( hir_id) {
1155+ Some ( match tcx. hir ( ) . get_by_hir_id ( hir_id) {
11401156 Node :: TraitItem ( item) => match item. node {
11411157 TraitItemKind :: Method ( ..) => {
11421158 let substs = InternalSubsts :: identity_for_item ( tcx, def_id) ;
11431159 tcx. mk_fn_def ( def_id, substs)
11441160 }
11451161 TraitItemKind :: Const ( ref ty, _) | TraitItemKind :: Type ( _, Some ( ref ty) ) => icx. to_ty ( ty) ,
11461162 TraitItemKind :: Type ( _, None ) => {
1163+ if !fail {
1164+ return None ;
1165+ }
11471166 span_bug ! ( item. span, "associated type missing default" ) ;
11481167 }
11491168 } ,
@@ -1225,6 +1244,9 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Ty<'tcx> {
12251244 | ItemKind :: GlobalAsm ( ..)
12261245 | ItemKind :: ExternCrate ( ..)
12271246 | ItemKind :: Use ( ..) => {
1247+ if !fail {
1248+ return None ;
1249+ }
12281250 span_bug ! (
12291251 item. span,
12301252 "compute_type_of_item: unexpected item type: {:?}" ,
@@ -1264,7 +1286,7 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Ty<'tcx> {
12641286 ..
12651287 } ) => {
12661288 if gen. is_some ( ) {
1267- return tcx. typeck_tables_of ( def_id) . node_type ( hir_id) ;
1289+ return Some ( tcx. typeck_tables_of ( def_id) . node_type ( hir_id) ) ;
12681290 }
12691291
12701292 let substs = ty:: ClosureSubsts {
@@ -1342,6 +1364,9 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Ty<'tcx> {
13421364 }
13431365 // Sanity check to make sure everything is as expected.
13441366 if !found_const {
1367+ if !fail {
1368+ return None ;
1369+ }
13451370 bug ! ( "no arg matching AnonConst in path" )
13461371 }
13471372 match path. def {
@@ -1367,14 +1392,27 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Ty<'tcx> {
13671392 return tcx. types . err ;
13681393 }
13691394 Def :: Err => tcx. types . err ,
1370- x => bug ! ( "unexpected const parent path def {:?}" , x) ,
1395+ x => {
1396+ if !fail {
1397+ return None ;
1398+ }
1399+ bug ! ( "unexpected const parent path def {:?}" , x) ;
1400+ }
1401+ }
1402+ }
1403+ x => {
1404+ if !fail {
1405+ return None ;
13711406 }
1407+ bug ! ( "unexpected const parent path {:?}" , x) ;
13721408 }
1373- x => bug ! ( "unexpected const parent path {:?}" , x) ,
13741409 }
13751410 }
13761411
13771412 x => {
1413+ if !fail {
1414+ return None ;
1415+ }
13781416 bug ! ( "unexpected const parent in type_of_def_id(): {:?}" , x) ;
13791417 }
13801418 }
@@ -1385,13 +1423,21 @@ fn type_of<'a, 'tcx>(tcx: TyCtxt<'a, 'tcx, 'tcx>, def_id: DefId) -> Ty<'tcx> {
13851423 hir:: GenericParamKind :: Const { ref ty, .. } => {
13861424 icx. to_ty ( ty)
13871425 }
1388- x => bug ! ( "unexpected non-type Node::GenericParam: {:?}" , x) ,
1426+ x => {
1427+ if !fail {
1428+ return None ;
1429+ }
1430+ bug ! ( "unexpected non-type Node::GenericParam: {:?}" , x)
1431+ } ,
13891432 } ,
13901433
13911434 x => {
1435+ if !fail {
1436+ return None ;
1437+ }
13921438 bug ! ( "unexpected sort of node in type_of_def_id(): {:?}" , x) ;
13931439 }
1394- }
1440+ } )
13951441}
13961442
13971443fn find_existential_constraints < ' a , ' tcx > (
0 commit comments