@@ -27,6 +27,7 @@ use rustc::hir::def_id::DefId;
2727use rustc:: infer:: canonical:: QueryRegionConstraint ;
2828use rustc:: infer:: outlives:: env:: RegionBoundPairs ;
2929use rustc:: infer:: { InferCtxt , InferOk , LateBoundRegionConversionTime , NLLRegionVariableOrigin } ;
30+ use rustc:: infer:: type_variable:: TypeVariableOrigin ;
3031use rustc:: mir:: interpret:: EvalErrorKind :: BoundsCheck ;
3132use rustc:: mir:: tcx:: PlaceTy ;
3233use rustc:: mir:: visit:: { PlaceContext , Visitor , MutatingUseContext , NonMutatingUseContext } ;
@@ -2074,15 +2075,163 @@ impl<'a, 'gcx, 'tcx> TypeChecker<'a, 'gcx, 'tcx> {
20742075 ) ;
20752076 }
20762077
2077- CastKind :: Misc => { }
2078+ CastKind :: MutToConstPointer => {
2079+ let ty_from = match op. ty ( mir, tcx) . sty {
2080+ ty:: RawPtr ( ty:: TypeAndMut {
2081+ ty : ty_from,
2082+ mutbl : hir:: MutMutable ,
2083+ } ) => ty_from,
2084+ _ => {
2085+ span_mirbug ! (
2086+ self ,
2087+ rvalue,
2088+ "unexpected base type for cast {:?}" ,
2089+ ty,
2090+ ) ;
2091+ return ;
2092+ }
2093+ } ;
2094+ let ty_to = match ty. sty {
2095+ ty:: RawPtr ( ty:: TypeAndMut {
2096+ ty : ty_to,
2097+ mutbl : hir:: MutImmutable ,
2098+ } ) => ty_to,
2099+ _ => {
2100+ span_mirbug ! (
2101+ self ,
2102+ rvalue,
2103+ "unexpected target type for cast {:?}" ,
2104+ ty,
2105+ ) ;
2106+ return ;
2107+ }
2108+ } ;
2109+ if let Err ( terr) = self . sub_types (
2110+ ty_from,
2111+ ty_to,
2112+ location. to_locations ( ) ,
2113+ ConstraintCategory :: Cast ,
2114+ ) {
2115+ span_mirbug ! (
2116+ self ,
2117+ rvalue,
2118+ "relating {:?} with {:?} yields {:?}" ,
2119+ ty_from,
2120+ ty_to,
2121+ terr
2122+ )
2123+ }
2124+ }
2125+
2126+ CastKind :: Misc => {
2127+ if let ty:: Ref ( _, mut ty_from, _) = op. ty ( mir, tcx) . sty {
2128+ let ( mut ty_to, mutability) = if let ty:: RawPtr ( ty:: TypeAndMut {
2129+ ty : ty_to,
2130+ mutbl,
2131+ } ) = ty. sty {
2132+ ( ty_to, mutbl)
2133+ } else {
2134+ span_mirbug ! (
2135+ self ,
2136+ rvalue,
2137+ "invalid cast types {:?} -> {:?}" ,
2138+ op. ty( mir, tcx) ,
2139+ ty,
2140+ ) ;
2141+ return ;
2142+ } ;
2143+
2144+ // Handle the direct cast from `&[T; N]` to `*const T` by unwrapping
2145+ // any array we find.
2146+ while let ty:: Array ( ty_elem_from, _) = ty_from. sty {
2147+ ty_from = ty_elem_from;
2148+ if let ty:: Array ( ty_elem_to, _) = ty_to. sty {
2149+ ty_to = ty_elem_to;
2150+ } else {
2151+ break ;
2152+ }
2153+ }
2154+
2155+ if let hir:: MutMutable = mutability {
2156+ if let Err ( terr) = self . eq_types (
2157+ ty_from,
2158+ ty_to,
2159+ location. to_locations ( ) ,
2160+ ConstraintCategory :: Cast ,
2161+ ) {
2162+ span_mirbug ! (
2163+ self ,
2164+ rvalue,
2165+ "equating {:?} with {:?} yields {:?}" ,
2166+ ty_from,
2167+ ty_to,
2168+ terr
2169+ )
2170+ }
2171+ } else {
2172+ if let Err ( terr) = self . sub_types (
2173+ ty_from,
2174+ ty_to,
2175+ location. to_locations ( ) ,
2176+ ConstraintCategory :: Cast ,
2177+ ) {
2178+ span_mirbug ! (
2179+ self ,
2180+ rvalue,
2181+ "relating {:?} with {:?} yields {:?}" ,
2182+ ty_from,
2183+ ty_to,
2184+ terr
2185+ )
2186+ }
2187+ }
2188+ }
2189+ }
20782190 }
20792191 }
20802192
20812193 Rvalue :: Ref ( region, _borrow_kind, borrowed_place) => {
20822194 self . add_reborrow_constraint ( mir, location, region, borrowed_place) ;
20832195 }
20842196
2085- // FIXME: These other cases have to be implemented in future PRs
2197+ Rvalue :: BinaryOp ( BinOp :: Eq , left, right)
2198+ | Rvalue :: BinaryOp ( BinOp :: Ne , left, right)
2199+ | Rvalue :: BinaryOp ( BinOp :: Lt , left, right)
2200+ | Rvalue :: BinaryOp ( BinOp :: Le , left, right)
2201+ | Rvalue :: BinaryOp ( BinOp :: Gt , left, right)
2202+ | Rvalue :: BinaryOp ( BinOp :: Ge , left, right) => {
2203+ let ty_left = left. ty ( mir, tcx) ;
2204+ if let ty:: RawPtr ( _) | ty:: FnPtr ( _) = ty_left. sty {
2205+ let ty_right = right. ty ( mir, tcx) ;
2206+ let common_ty = self . infcx . next_ty_var (
2207+ TypeVariableOrigin :: MiscVariable ( mir. source_info ( location) . span ) ,
2208+ ) ;
2209+ self . sub_types (
2210+ common_ty,
2211+ ty_left,
2212+ location. to_locations ( ) ,
2213+ ConstraintCategory :: Boring
2214+ ) . unwrap_or_else ( |err| {
2215+ bug ! ( "Could not equate type variable with {:?}: {:?}" , ty_left, err)
2216+ } ) ;
2217+ if let Err ( terr) = self . sub_types (
2218+ common_ty,
2219+ ty_right,
2220+ location. to_locations ( ) ,
2221+ ConstraintCategory :: Boring
2222+ ) {
2223+ span_mirbug ! (
2224+ self ,
2225+ rvalue,
2226+ "unexpected comparison types {:?} and {:?} yields {:?}" ,
2227+ ty_left,
2228+ ty_right,
2229+ terr
2230+ )
2231+ }
2232+ }
2233+ }
2234+
20862235 Rvalue :: Use ( ..)
20872236 | Rvalue :: Len ( ..)
20882237 | Rvalue :: BinaryOp ( ..)
0 commit comments