2019-05-01 10:06:11 -05:00
//! Conversion code from/to Chalk.
2020-05-22 10:14:53 -05:00
use std ::sync ::Arc ;
2019-05-01 10:06:11 -05:00
2019-05-01 13:50:49 -05:00
use log ::debug ;
2020-05-22 10:14:53 -05:00
use chalk_ir ::{ fold ::shift ::Shift , GenericArg , TypeName } ;
2019-05-01 10:06:11 -05:00
2020-05-18 14:25:23 -05:00
use hir_def ::{
2020-05-22 08:55:15 -05:00
lang_item ::{ lang_attr , LangItemTarget } ,
2020-05-22 10:14:53 -05:00
AssocContainerId , AssocItemId , HasModule , Lookup , TypeAliasId ,
2019-11-26 09:00:36 -06:00
} ;
2020-05-22 10:14:53 -05:00
use ra_db ::{ salsa ::InternKey , CrateId } ;
2019-05-01 10:06:11 -05:00
2020-05-22 10:14:53 -05:00
use super ::{ builtin , AssocTyValue , ChalkContext , Impl } ;
2019-05-01 10:06:11 -05:00
use crate ::{
2020-05-22 10:14:53 -05:00
db ::HirDatabase , display ::HirDisplay , method_resolution ::TyFingerprint , utils ::generics ,
2020-05-22 11:15:53 -05:00
CallableDef , DebruijnIndex , GenericPredicate , Substs , Ty , TypeCtor ,
2019-05-01 10:06:11 -05:00
} ;
2020-05-22 08:55:15 -05:00
use chalk_rust_ir ::WellKnownTrait ;
2020-05-22 10:14:53 -05:00
use mapping ::{ convert_where_clauses , generic_predicate_to_inline_bound , make_binders } ;
2019-05-01 10:06:11 -05:00
2020-05-22 10:14:53 -05:00
pub use self ::interner ::* ;
2020-04-10 10:44:29 -05:00
2020-05-22 10:14:53 -05:00
pub ( super ) mod tls ;
mod interner ;
mod mapping ;
2019-12-21 07:29:33 -06:00
2019-05-01 10:06:11 -05:00
pub ( super ) trait ToChalk {
type Chalk ;
2020-03-13 10:05:46 -05:00
fn to_chalk ( self , db : & dyn HirDatabase ) -> Self ::Chalk ;
fn from_chalk ( db : & dyn HirDatabase , chalk : Self ::Chalk ) -> Self ;
2019-05-01 10:06:11 -05:00
}
2020-03-13 10:05:46 -05:00
pub ( super ) fn from_chalk < T , ChalkT > ( db : & dyn HirDatabase , chalk : ChalkT ) -> T
2019-05-01 10:06:11 -05:00
where
T : ToChalk < Chalk = ChalkT > ,
{
T ::from_chalk ( db , chalk )
}
2020-03-13 10:05:46 -05:00
impl < ' a > chalk_solve ::RustIrDatabase < Interner > for ChalkContext < ' a > {
2019-12-21 07:29:33 -06:00
fn associated_ty_data ( & self , id : AssocTypeId ) -> Arc < AssociatedTyDatum > {
2019-06-26 04:54:13 -05:00
self . db . associated_ty_data ( id )
2019-05-01 10:06:11 -05:00
}
2019-12-21 07:29:33 -06:00
fn trait_datum ( & self , trait_id : TraitId ) -> Arc < TraitDatum > {
2019-06-26 04:54:13 -05:00
self . db . trait_datum ( self . krate , trait_id )
2019-05-01 10:06:11 -05:00
}
2020-05-22 10:50:58 -05:00
fn adt_datum ( & self , struct_id : AdtId ) -> Arc < StructDatum > {
2019-06-26 04:54:13 -05:00
self . db . struct_datum ( self . krate , struct_id )
2019-05-01 10:06:11 -05:00
}
2019-12-21 07:29:33 -06:00
fn impl_datum ( & self , impl_id : ImplId ) -> Arc < ImplDatum > {
2019-06-26 04:54:13 -05:00
self . db . impl_datum ( self . krate , impl_id )
2019-05-01 10:06:11 -05:00
}
2020-05-22 09:40:42 -05:00
fn fn_def_datum (
& self ,
2020-05-22 11:15:53 -05:00
fn_def_id : chalk_ir ::FnDefId < Interner > ,
2020-05-22 09:40:42 -05:00
) -> Arc < chalk_rust_ir ::FnDefDatum < Interner > > {
2020-05-22 11:15:53 -05:00
self . db . fn_def_datum ( self . krate , fn_def_id )
2020-05-22 09:40:42 -05:00
}
2019-09-24 11:27:31 -05:00
fn impls_for_trait (
& self ,
2019-12-21 07:29:33 -06:00
trait_id : TraitId ,
2020-05-22 09:40:42 -05:00
parameters : & [ GenericArg < Interner > ] ,
2019-12-21 07:29:33 -06:00
) -> Vec < ImplId > {
2019-05-01 13:50:49 -05:00
debug! ( " impls_for_trait {:?} " , trait_id ) ;
2019-12-21 07:29:33 -06:00
let trait_ : hir_def ::TraitId = from_chalk ( self . db , trait_id ) ;
2019-12-21 08:00:44 -06:00
2020-04-11 06:11:33 -05:00
let ty : Ty = from_chalk ( self . db , parameters [ 0 ] . assert_ty_ref ( & Interner ) . clone ( ) ) ;
let self_ty_fp = TyFingerprint ::for_impl ( & ty ) ;
2019-12-21 08:00:44 -06:00
// Note: Since we're using impls_for_trait, only impls where the trait
// can be resolved should ever reach Chalk. `impl_datum` relies on that
// and will panic if the trait can't be resolved.
2019-09-09 15:10:58 -05:00
let mut result : Vec < _ > = self
2019-05-07 10:35:45 -05:00
. db
2020-04-11 06:11:33 -05:00
. impls_for_trait ( self . krate , trait_ , self_ty_fp )
2019-05-01 10:06:11 -05:00
. iter ( )
2019-09-09 15:10:58 -05:00
. copied ( )
2020-02-29 14:24:40 -06:00
. map ( Impl ::ImplDef )
2019-09-09 15:10:58 -05:00
. map ( | impl_ | impl_ . to_chalk ( self . db ) )
2019-05-07 10:35:45 -05:00
. collect ( ) ;
2019-09-09 15:10:58 -05:00
2020-02-21 12:05:27 -06:00
let arg : Option < Ty > =
2020-03-27 08:50:08 -05:00
parameters . get ( 1 ) . map ( | p | from_chalk ( self . db , p . assert_ty_ref ( & Interner ) . clone ( ) ) ) ;
2019-12-03 05:16:39 -06:00
2020-02-21 12:05:27 -06:00
builtin ::get_builtin_impls ( self . db , self . krate , & ty , & arg , trait_ , | i | {
2019-12-03 05:16:39 -06:00
result . push ( i . to_chalk ( self . db ) )
} ) ;
2019-09-09 15:10:58 -05:00
2019-05-07 10:35:45 -05:00
debug! ( " impls_for_trait returned {} impls " , result . len ( ) ) ;
result
2019-05-01 10:06:11 -05:00
}
2020-05-22 10:50:58 -05:00
fn impl_provided_for ( & self , auto_trait_id : TraitId , struct_id : AdtId ) -> bool {
2019-05-01 13:50:49 -05:00
debug! ( " impl_provided_for {:?}, {:?} " , auto_trait_id , struct_id ) ;
2019-05-01 10:06:11 -05:00
false // FIXME
}
2019-12-21 07:29:33 -06:00
fn associated_ty_value ( & self , id : AssociatedTyValueId ) -> Arc < AssociatedTyValue > {
2020-02-18 06:53:02 -06:00
self . db . associated_ty_value ( self . krate , id )
2019-05-01 10:06:11 -05:00
}
2020-02-24 14:36:57 -06:00
fn custom_clauses ( & self ) -> Vec < chalk_ir ::ProgramClause < Interner > > {
2019-05-01 16:26:42 -05:00
vec! [ ]
}
2019-12-21 07:29:33 -06:00
fn local_impls_to_coherence_check ( & self , _trait_id : TraitId ) -> Vec < ImplId > {
2019-09-23 13:33:47 -05:00
// We don't do coherence checking (yet)
unimplemented! ( )
2019-05-01 16:26:42 -05:00
}
2020-03-02 16:01:16 -06:00
fn interner ( & self ) -> & Interner {
& Interner
}
2020-04-10 10:44:29 -05:00
fn well_known_trait_id (
& self ,
2020-05-22 08:55:15 -05:00
well_known_trait : chalk_rust_ir ::WellKnownTrait ,
2020-04-16 05:39:00 -05:00
) -> Option < chalk_ir ::TraitId < Interner > > {
2020-05-22 08:55:15 -05:00
let lang_attr = lang_attr_from_well_known_trait ( well_known_trait ) ;
let lang_items = self . db . crate_lang_items ( self . krate ) ;
let trait_ = match lang_items . target ( lang_attr ) {
Some ( LangItemTarget ::TraitId ( trait_ ) ) = > trait_ ,
_ = > return None ,
} ;
Some ( trait_ . to_chalk ( self . db ) )
2020-04-10 10:44:29 -05:00
}
2020-04-18 06:36:35 -05:00
fn program_clauses_for_env (
& self ,
environment : & chalk_ir ::Environment < Interner > ,
) -> chalk_ir ::ProgramClauses < Interner > {
self . db . program_clauses_for_chalk_env ( self . krate , environment . clone ( ) )
}
fn opaque_ty_data (
& self ,
_id : chalk_ir ::OpaqueTyId < Interner > ,
) -> Arc < chalk_rust_ir ::OpaqueTyDatum < Interner > > {
unimplemented! ( )
}
2020-05-16 03:49:43 -05:00
fn force_impl_for (
& self ,
_well_known : chalk_rust_ir ::WellKnownTrait ,
_ty : & chalk_ir ::TyData < Interner > ,
) -> Option < bool > {
// this method is mostly for rustc
None
}
fn is_object_safe ( & self , _trait_id : chalk_ir ::TraitId < Interner > ) -> bool {
// FIXME: implement actual object safety
true
}
2020-04-18 06:36:35 -05:00
}
pub ( crate ) fn program_clauses_for_chalk_env_query (
db : & dyn HirDatabase ,
krate : CrateId ,
environment : chalk_ir ::Environment < Interner > ,
) -> chalk_ir ::ProgramClauses < Interner > {
chalk_solve ::program_clauses_for_env ( & ChalkContext { db , krate } , & environment )
2019-05-01 10:06:11 -05:00
}
2019-06-26 04:54:13 -05:00
pub ( crate ) fn associated_ty_data_query (
2020-03-13 10:05:46 -05:00
db : & dyn HirDatabase ,
2019-12-21 07:29:33 -06:00
id : AssocTypeId ,
) -> Arc < AssociatedTyDatum > {
2019-06-26 04:54:13 -05:00
debug! ( " associated_ty_data {:?} " , id ) ;
2019-11-25 09:58:17 -06:00
let type_alias : TypeAliasId = from_chalk ( db , id ) ;
2020-03-13 10:05:46 -05:00
let trait_ = match type_alias . lookup ( db . upcast ( ) ) . container {
2019-12-20 04:59:50 -06:00
AssocContainerId ::TraitId ( t ) = > t ,
2019-06-26 04:54:13 -05:00
_ = > panic! ( " associated type not in trait " ) ,
} ;
2020-04-12 05:28:24 -05:00
// Lower bounds -- we could/should maybe move this to a separate query in `lower`
let type_alias_data = db . type_alias_data ( type_alias ) ;
2020-03-13 10:05:46 -05:00
let generic_params = generics ( db . upcast ( ) , type_alias . into ( ) ) ;
2020-04-17 15:48:29 -05:00
let bound_vars = Substs ::bound_vars ( & generic_params , DebruijnIndex ::INNERMOST ) ;
2020-04-12 05:28:24 -05:00
let resolver = hir_def ::resolver ::HasResolver ::resolver ( type_alias , db . upcast ( ) ) ;
let ctx = crate ::TyLoweringContext ::new ( db , & resolver )
. with_type_param_mode ( crate ::lower ::TypeParamLoweringMode ::Variable ) ;
let self_ty = Ty ::Bound ( crate ::BoundVar ::new ( crate ::DebruijnIndex ::INNERMOST , 0 ) ) ;
let bounds = type_alias_data
. bounds
. iter ( )
. flat_map ( | bound | GenericPredicate ::from_type_bound ( & ctx , bound , self_ty . clone ( ) ) )
. filter_map ( | pred | generic_predicate_to_inline_bound ( db , & pred , & self_ty ) )
. map ( | bound | make_binders ( bound . shifted_in ( & Interner ) , 0 ) )
. collect ( ) ;
let where_clauses = convert_where_clauses ( db , type_alias . into ( ) , & bound_vars ) ;
let bound_data = chalk_rust_ir ::AssociatedTyDatumBound { bounds , where_clauses } ;
2019-06-26 04:54:13 -05:00
let datum = AssociatedTyDatum {
2019-11-26 09:00:36 -06:00
trait_id : trait_ . to_chalk ( db ) ,
2019-06-26 04:54:13 -05:00
id ,
2020-03-02 23:57:16 -06:00
name : type_alias ,
2019-12-07 06:05:05 -06:00
binders : make_binders ( bound_data , generic_params . len ( ) ) ,
2019-06-26 04:54:13 -05:00
} ;
Arc ::new ( datum )
}
pub ( crate ) fn trait_datum_query (
2020-03-13 10:05:46 -05:00
db : & dyn HirDatabase ,
2019-11-27 00:42:55 -06:00
krate : CrateId ,
2019-12-21 07:29:33 -06:00
trait_id : TraitId ,
) -> Arc < TraitDatum > {
2019-06-26 04:54:13 -05:00
debug! ( " trait_datum {:?} " , trait_id ) ;
2019-12-21 07:29:33 -06:00
let trait_ : hir_def ::TraitId = from_chalk ( db , trait_id ) ;
2019-11-26 09:00:36 -06:00
let trait_data = db . trait_data ( trait_ ) ;
debug! ( " trait {:?} = {:?} " , trait_id , trait_data . name ) ;
2020-03-13 10:05:46 -05:00
let generic_params = generics ( db . upcast ( ) , trait_ . into ( ) ) ;
2020-04-17 15:48:29 -05:00
let bound_vars = Substs ::bound_vars ( & generic_params , DebruijnIndex ::INNERMOST ) ;
2019-06-26 04:54:13 -05:00
let flags = chalk_rust_ir ::TraitFlags {
2019-11-26 09:00:36 -06:00
auto : trait_data . auto ,
2020-03-13 10:05:46 -05:00
upstream : trait_ . lookup ( db . upcast ( ) ) . container . module ( db . upcast ( ) ) . krate ! = krate ,
2019-09-09 14:24:24 -05:00
non_enumerable : true ,
2019-11-15 13:32:58 -06:00
coinductive : false , // only relevant for Chalk testing
2019-06-26 04:54:13 -05:00
// FIXME set these flags correctly
marker : false ,
fundamental : false ,
} ;
2019-11-26 09:00:36 -06:00
let where_clauses = convert_where_clauses ( db , trait_ . into ( ) , & bound_vars ) ;
let associated_ty_ids =
trait_data . associated_types ( ) . map ( | type_alias | type_alias . to_chalk ( db ) ) . collect ( ) ;
2019-11-15 13:32:58 -06:00
let trait_datum_bound = chalk_rust_ir ::TraitDatumBound { where_clauses } ;
2020-05-22 08:55:15 -05:00
let well_known =
lang_attr ( db . upcast ( ) , trait_ ) . and_then ( | name | well_known_trait_from_lang_attr ( & name ) ) ;
2019-11-15 13:32:58 -06:00
let trait_datum = TraitDatum {
id : trait_id ,
binders : make_binders ( trait_datum_bound , bound_vars . len ( ) ) ,
flags ,
associated_ty_ids ,
2020-04-05 11:24:18 -05:00
well_known ,
2019-11-15 13:32:58 -06:00
} ;
2019-06-26 04:54:13 -05:00
Arc ::new ( trait_datum )
}
2020-05-22 08:55:15 -05:00
fn well_known_trait_from_lang_attr ( name : & str ) -> Option < WellKnownTrait > {
Some ( match name {
" sized " = > WellKnownTrait ::SizedTrait ,
" copy " = > WellKnownTrait ::CopyTrait ,
" clone " = > WellKnownTrait ::CloneTrait ,
" drop " = > WellKnownTrait ::DropTrait ,
_ = > return None ,
} )
}
fn lang_attr_from_well_known_trait ( attr : WellKnownTrait ) -> & 'static str {
match attr {
WellKnownTrait ::SizedTrait = > " sized " ,
WellKnownTrait ::CopyTrait = > " copy " ,
WellKnownTrait ::CloneTrait = > " clone " ,
WellKnownTrait ::DropTrait = > " drop " ,
}
}
2019-06-26 04:54:13 -05:00
pub ( crate ) fn struct_datum_query (
2020-03-13 10:05:46 -05:00
db : & dyn HirDatabase ,
2019-11-27 00:42:55 -06:00
krate : CrateId ,
2020-05-22 10:50:58 -05:00
struct_id : AdtId ,
2019-12-21 07:29:33 -06:00
) -> Arc < StructDatum > {
2019-06-26 04:54:13 -05:00
debug! ( " struct_datum {:?} " , struct_id ) ;
2020-05-22 09:40:42 -05:00
let type_ctor : TypeCtor = from_chalk ( db , TypeName ::Adt ( struct_id ) ) ;
2019-06-26 04:54:13 -05:00
debug! ( " struct {:?} = {:?} " , struct_id , type_ctor ) ;
2019-09-26 14:37:03 -05:00
let num_params = type_ctor . num_ty_params ( db ) ;
let upstream = type_ctor . krate ( db ) ! = Some ( krate ) ;
let where_clauses = type_ctor
. as_generic_def ( )
. map ( | generic_def | {
2020-03-13 10:05:46 -05:00
let generic_params = generics ( db . upcast ( ) , generic_def ) ;
2020-04-17 15:48:29 -05:00
let bound_vars = Substs ::bound_vars ( & generic_params , DebruijnIndex ::INNERMOST ) ;
2019-09-26 14:37:03 -05:00
convert_where_clauses ( db , generic_def , & bound_vars )
} )
. unwrap_or_else ( Vec ::new ) ;
2020-05-22 09:40:42 -05:00
let flags = chalk_rust_ir ::AdtFlags {
2019-06-26 04:54:13 -05:00
upstream ,
// FIXME set fundamental flag correctly
fundamental : false ,
} ;
2020-05-22 09:40:42 -05:00
let struct_datum_bound = chalk_rust_ir ::AdtDatumBound {
2019-06-26 04:54:13 -05:00
fields : Vec ::new ( ) , // FIXME add fields (only relevant for auto traits)
where_clauses ,
} ;
2019-11-15 13:32:58 -06:00
let struct_datum =
StructDatum { id : struct_id , binders : make_binders ( struct_datum_bound , num_params ) , flags } ;
2019-06-26 04:54:13 -05:00
Arc ::new ( struct_datum )
}
pub ( crate ) fn impl_datum_query (
2020-03-13 10:05:46 -05:00
db : & dyn HirDatabase ,
2019-11-27 00:42:55 -06:00
krate : CrateId ,
2019-12-21 07:29:33 -06:00
impl_id : ImplId ,
) -> Arc < ImplDatum > {
2019-06-26 04:54:13 -05:00
let _p = ra_prof ::profile ( " impl_datum " ) ;
debug! ( " impl_datum {:?} " , impl_id ) ;
2019-09-09 15:10:58 -05:00
let impl_ : Impl = from_chalk ( db , impl_id ) ;
match impl_ {
2020-02-29 14:24:40 -06:00
Impl ::ImplDef ( impl_def ) = > impl_def_datum ( db , krate , impl_id , impl_def ) ,
2019-12-21 08:00:44 -06:00
_ = > Arc ::new ( builtin ::impl_datum ( db , krate , impl_ ) . to_chalk ( db ) ) ,
2019-09-09 15:10:58 -05:00
}
}
2020-02-29 14:24:40 -06:00
fn impl_def_datum (
2020-03-13 10:05:46 -05:00
db : & dyn HirDatabase ,
2019-11-27 00:42:55 -06:00
krate : CrateId ,
2019-12-21 07:29:33 -06:00
chalk_id : ImplId ,
impl_id : hir_def ::ImplId ,
2019-12-21 08:00:44 -06:00
) -> Arc < ImplDatum > {
let trait_ref = db
. impl_trait ( impl_id )
// ImplIds for impls where the trait ref can't be resolved should never reach Chalk
2020-01-31 09:52:43 -06:00
. expect ( " invalid impl passed to Chalk " )
. value ;
2019-11-27 03:47:18 -06:00
let impl_data = db . impl_data ( impl_id ) ;
2020-03-13 10:05:46 -05:00
let generic_params = generics ( db . upcast ( ) , impl_id . into ( ) ) ;
2020-04-17 15:48:29 -05:00
let bound_vars = Substs ::bound_vars ( & generic_params , DebruijnIndex ::INNERMOST ) ;
2019-11-15 13:32:58 -06:00
let trait_ = trait_ref . trait_ ;
2020-03-13 10:05:46 -05:00
let impl_type = if impl_id . lookup ( db . upcast ( ) ) . container . module ( db . upcast ( ) ) . krate = = krate {
2019-06-26 04:54:13 -05:00
chalk_rust_ir ::ImplType ::Local
} else {
chalk_rust_ir ::ImplType ::External
} ;
2019-11-27 03:47:18 -06:00
let where_clauses = convert_where_clauses ( db , impl_id . into ( ) , & bound_vars ) ;
let negative = impl_data . is_negative ;
2019-06-26 04:54:13 -05:00
debug! (
" impl {:?}: {}{} where {:?} " ,
2019-11-27 03:47:18 -06:00
chalk_id ,
2019-06-26 04:54:13 -05:00
if negative { " ! " } else { " " } ,
trait_ref . display ( db ) ,
where_clauses
) ;
let trait_ref = trait_ref . to_chalk ( db ) ;
2019-10-10 13:51:50 -05:00
let polarity = if negative {
chalk_rust_ir ::Polarity ::Negative
} else {
chalk_rust_ir ::Polarity ::Positive
2019-06-26 04:54:13 -05:00
} ;
2019-10-10 13:51:50 -05:00
2019-11-15 13:32:58 -06:00
let impl_datum_bound = chalk_rust_ir ::ImplDatumBound { trait_ref , where_clauses } ;
2019-11-26 09:00:36 -06:00
let trait_data = db . trait_data ( trait_ ) ;
2019-11-27 03:47:18 -06:00
let associated_ty_value_ids = impl_data
. items
. iter ( )
2019-11-15 13:32:58 -06:00
. filter_map ( | item | match item {
2019-11-27 03:47:18 -06:00
AssocItemId ::TypeAliasId ( type_alias ) = > Some ( * type_alias ) ,
2019-11-15 13:32:58 -06:00
_ = > None ,
} )
2019-11-27 03:47:18 -06:00
. filter ( | & type_alias | {
2019-11-15 13:32:58 -06:00
// don't include associated types that don't exist in the trait
2019-11-27 03:47:18 -06:00
let name = & db . type_alias_data ( type_alias ) . name ;
trait_data . associated_type_by_name ( name ) . is_some ( )
2019-11-15 13:32:58 -06:00
} )
2019-11-27 03:47:18 -06:00
. map ( | type_alias | AssocTyValue ::TypeAlias ( type_alias ) . to_chalk ( db ) )
2019-11-15 13:32:58 -06:00
. collect ( ) ;
2019-06-26 04:54:13 -05:00
debug! ( " impl_datum: {:?} " , impl_datum_bound ) ;
2019-10-10 13:51:50 -05:00
let impl_datum = ImplDatum {
binders : make_binders ( impl_datum_bound , bound_vars . len ( ) ) ,
impl_type ,
polarity ,
2019-11-15 13:32:58 -06:00
associated_ty_value_ids ,
2019-10-10 13:51:50 -05:00
} ;
2019-09-09 15:10:58 -05:00
Arc ::new ( impl_datum )
}
2019-11-15 13:32:58 -06:00
pub ( crate ) fn associated_ty_value_query (
2020-03-13 10:05:46 -05:00
db : & dyn HirDatabase ,
2019-11-27 00:42:55 -06:00
krate : CrateId ,
2019-12-21 07:46:15 -06:00
id : AssociatedTyValueId ,
) -> Arc < AssociatedTyValue > {
2019-11-15 13:32:58 -06:00
let data : AssocTyValue = from_chalk ( db , id ) ;
match data {
AssocTyValue ::TypeAlias ( type_alias ) = > {
type_alias_associated_ty_value ( db , krate , type_alias )
}
2019-12-03 05:16:39 -06:00
_ = > Arc ::new ( builtin ::associated_ty_value ( db , krate , data ) . to_chalk ( db ) ) ,
2019-11-15 13:32:58 -06:00
}
}
fn type_alias_associated_ty_value (
2020-03-13 10:05:46 -05:00
db : & dyn HirDatabase ,
2019-11-27 00:42:55 -06:00
_krate : CrateId ,
2019-11-27 02:40:10 -06:00
type_alias : TypeAliasId ,
2019-12-21 07:29:33 -06:00
) -> Arc < AssociatedTyValue > {
2019-11-27 02:40:10 -06:00
let type_alias_data = db . type_alias_data ( type_alias ) ;
2020-03-13 10:05:46 -05:00
let impl_id = match type_alias . lookup ( db . upcast ( ) ) . container {
2019-12-20 04:59:50 -06:00
AssocContainerId ::ImplId ( it ) = > it ,
2019-11-27 02:40:10 -06:00
_ = > panic! ( " assoc ty value should be in impl " ) ,
} ;
2020-01-31 09:52:43 -06:00
let trait_ref = db . impl_trait ( impl_id ) . expect ( " assoc ty value should not exist " ) . value ; // we don't return any assoc ty values if the impl'd trait can't be resolved
2019-11-27 02:40:10 -06:00
2019-11-26 08:21:29 -06:00
let assoc_ty = db
2019-11-27 13:12:09 -06:00
. trait_data ( trait_ref . trait_ )
2019-11-27 02:40:10 -06:00
. associated_type_by_name ( & type_alias_data . name )
2019-11-26 08:21:29 -06:00
. expect ( " assoc ty value should not exist " ) ; // validated when building the impl data as well
2020-01-31 09:52:43 -06:00
let ty = db . ty ( type_alias . into ( ) ) ;
let value_bound = chalk_rust_ir ::AssociatedTyValueBound { ty : ty . value . to_chalk ( db ) } ;
2019-11-15 13:32:58 -06:00
let value = chalk_rust_ir ::AssociatedTyValue {
2020-02-29 14:24:40 -06:00
impl_id : Impl ::ImplDef ( impl_id ) . to_chalk ( db ) ,
2019-11-15 13:32:58 -06:00
associated_ty_id : assoc_ty . to_chalk ( db ) ,
2020-01-31 09:52:43 -06:00
value : make_binders ( value_bound , ty . num_binders ) ,
2019-11-15 13:32:58 -06:00
} ;
Arc ::new ( value )
}
2020-05-22 11:15:53 -05:00
pub ( crate ) fn fn_def_datum_query (
db : & dyn HirDatabase ,
_krate : CrateId ,
fn_def_id : FnDefId ,
) -> Arc < FnDefDatum > {
let callable_def : CallableDef = from_chalk ( db , fn_def_id ) ;
let generic_params = generics ( db . upcast ( ) , callable_def . into ( ) ) ;
let sig = db . callable_item_signature ( callable_def ) ;
let bound_vars = Substs ::bound_vars ( & generic_params , DebruijnIndex ::INNERMOST ) ;
let where_clauses = convert_where_clauses ( db , callable_def . into ( ) , & bound_vars ) ;
let bound = chalk_rust_ir ::FnDefDatumBound {
// Note: Chalk doesn't actually use this information yet as far as I am aware, but we provide it anyway
argument_types : sig . value . params ( ) . iter ( ) . map ( | ty | ty . clone ( ) . to_chalk ( db ) ) . collect ( ) ,
return_type : sig . value . ret ( ) . clone ( ) . to_chalk ( db ) ,
where_clauses ,
} ;
let datum = FnDefDatum { id : fn_def_id , binders : make_binders ( bound , sig . num_binders ) } ;
Arc ::new ( datum )
}
2020-05-22 10:50:58 -05:00
impl From < AdtId > for crate ::TypeCtorId {
fn from ( struct_id : AdtId ) -> Self {
struct_id . 0
2019-05-01 10:06:11 -05:00
}
}
2020-05-22 10:50:58 -05:00
impl From < crate ::TypeCtorId > for AdtId {
2019-11-27 08:46:02 -06:00
fn from ( type_ctor_id : crate ::TypeCtorId ) -> Self {
2020-05-22 10:50:58 -05:00
chalk_ir ::AdtId ( type_ctor_id )
2019-05-01 10:06:11 -05:00
}
}
2020-05-22 11:15:53 -05:00
impl From < FnDefId > for crate ::CallableDefId {
fn from ( fn_def_id : FnDefId ) -> Self {
InternKey ::from_intern_id ( fn_def_id . 0 )
}
}
impl From < crate ::CallableDefId > for FnDefId {
fn from ( callable_def_id : crate ::CallableDefId ) -> Self {
chalk_ir ::FnDefId ( callable_def_id . as_intern_id ( ) )
}
}
2019-12-21 07:29:33 -06:00
impl From < ImplId > for crate ::traits ::GlobalImplId {
fn from ( impl_id : ImplId ) -> Self {
2019-12-21 08:00:44 -06:00
InternKey ::from_intern_id ( impl_id . 0 )
2019-05-01 10:06:11 -05:00
}
}
2019-12-21 07:29:33 -06:00
impl From < crate ::traits ::GlobalImplId > for ImplId {
2019-11-27 08:46:02 -06:00
fn from ( impl_id : crate ::traits ::GlobalImplId ) -> Self {
2019-12-21 08:00:44 -06:00
chalk_ir ::ImplId ( impl_id . as_intern_id ( ) )
2019-05-01 10:06:11 -05:00
}
}
2019-11-15 13:32:58 -06:00
2020-03-02 15:30:38 -06:00
impl From < chalk_rust_ir ::AssociatedTyValueId < Interner > > for crate ::traits ::AssocTyValueId {
fn from ( id : chalk_rust_ir ::AssociatedTyValueId < Interner > ) -> Self {
Self ::from_intern_id ( id . 0 )
2019-11-15 13:32:58 -06:00
}
}
2020-03-02 15:30:38 -06:00
impl From < crate ::traits ::AssocTyValueId > for chalk_rust_ir ::AssociatedTyValueId < Interner > {
2019-11-27 08:46:02 -06:00
fn from ( assoc_ty_value_id : crate ::traits ::AssocTyValueId ) -> Self {
2020-03-02 15:30:38 -06:00
chalk_rust_ir ::AssociatedTyValueId ( assoc_ty_value_id . as_intern_id ( ) )
2019-11-15 13:32:58 -06:00
}
}