|
12 | 12 | // unresolved type variables and replaces "ty_var" types with their
|
13 | 13 | // substitutions.
|
14 | 14 |
|
15 |
| -use check::{FnCtxt, LvalueOp}; |
| 15 | +use check::FnCtxt; |
16 | 16 | use rustc::hir;
|
17 | 17 | use rustc::hir::def_id::{DefId, DefIndex};
|
18 | 18 | use rustc::hir::intravisit::{self, NestedVisitorMap, Visitor};
|
19 | 19 | use rustc::infer::InferCtxt;
|
20 |
| -use rustc::ty::{self, LvaluePreference, Ty, TyCtxt}; |
| 20 | +use rustc::ty::{self, Ty, TyCtxt}; |
21 | 21 | use rustc::ty::adjustment::{Adjust, Adjustment};
|
22 | 22 | use rustc::ty::fold::{TypeFoldable, TypeFolder};
|
23 | 23 | use rustc::util::nodemap::DefIdSet;
|
@@ -167,73 +167,34 @@ impl<'cx, 'gcx, 'tcx> WritebackCx<'cx, 'gcx, 'tcx> {
|
167 | 167 | // usize-ish
|
168 | 168 | fn fix_index_builtin_expr(&mut self, e: &hir::Expr) {
|
169 | 169 | if let hir::ExprIndex(ref base, ref index) = e.node {
|
170 |
| - let base_ty = self.fcx.node_ty(base.hir_id); |
| 170 | + let mut tables = self.fcx.tables.borrow_mut(); |
| 171 | + |
| 172 | + let base_ty = tables.expr_ty_adjusted(&base); |
171 | 173 | let base_ty = self.fcx.resolve_type_vars_if_possible(&base_ty);
|
172 |
| - let index_ty = self.fcx.node_ty(index.hir_id); |
| 174 | + let index_ty = tables.expr_ty_adjusted(&index); |
173 | 175 | let index_ty = self.fcx.resolve_type_vars_if_possible(&index_ty);
|
174 | 176 |
|
175 |
| - if index_ty.is_uint() { |
176 |
| - // HACK: the *actual* type being indexed is not stored anywhere |
177 |
| - // so we try to find it again here by derefs |
178 |
| - let mut autoderef = self.fcx.autoderef(e.span, base_ty); |
179 |
| - let builtin_ty : Option<_> = { |
180 |
| - loop { |
181 |
| - // This is essentially a duplicate of the index discovery |
182 |
| - // logic in typechecking code |
183 |
| - // Find the first type dereffable to which has builtin |
184 |
| - // indexing - this |
185 |
| - if let Some(_) = autoderef.next() { |
186 |
| - let current_ty = autoderef.unambiguous_final_ty(); |
187 |
| - |
188 |
| - if current_ty.builtin_index().is_some() { |
189 |
| - // If there is a builtin index, use it |
190 |
| - break Some(current_ty); |
191 |
| - } else { |
192 |
| - // If there's an overloaded index which happens |
193 |
| - // to take a uint, stop looking - otherwise we |
194 |
| - // might incorrectly deref further |
195 |
| - let overloaded_method = |
196 |
| - self.fcx.try_overloaded_lvalue_op( |
197 |
| - e.span, |
198 |
| - base_ty, |
199 |
| - &[index_ty], |
200 |
| - LvaluePreference::NoPreference, |
201 |
| - LvalueOp::Index |
202 |
| - ); |
203 |
| - |
204 |
| - if overloaded_method.is_some() { |
205 |
| - break None; |
206 |
| - } |
207 |
| - } |
208 |
| - } else { |
209 |
| - break None; |
210 |
| - } |
| 177 | + if base_ty.builtin_index().is_some() && index_ty.is_uint() { |
| 178 | + |
| 179 | + // Remove the method call record, which blocks use in |
| 180 | + // constant or static cases |
| 181 | + tables.type_dependent_defs_mut().remove(e.hir_id); |
| 182 | + tables.node_substs_mut().remove(e.hir_id); |
| 183 | + |
| 184 | + tables.adjustments_mut().get_mut(base.hir_id).map(|a| { |
| 185 | + // Discard the need for a mutable borrow |
| 186 | + match a.pop() { |
| 187 | + // Extra adjustment made when indexing causes a drop |
| 188 | + // of size information - we need to get rid of it |
| 189 | + // Since this is "after" the other adjustment to be |
| 190 | + // discarded, we do an extra `pop()` |
| 191 | + Some(Adjustment { kind: Adjust::Unsize, .. }) => { |
| 192 | + // So the borrow discard actually happens here |
| 193 | + a.pop(); |
| 194 | + }, |
| 195 | + _ => {} |
211 | 196 | }
|
212 |
| - }; |
213 |
| - |
214 |
| - if builtin_ty.is_some() { |
215 |
| - let mut tables = self.fcx.tables.borrow_mut(); |
216 |
| - |
217 |
| - // Remove the method call record, which blocks use in |
218 |
| - // constant or static cases |
219 |
| - tables.type_dependent_defs_mut().remove(e.hir_id); |
220 |
| - tables.node_substs_mut().remove(e.hir_id); |
221 |
| - |
222 |
| - tables.adjustments_mut().get_mut(base.hir_id).map(|a| { |
223 |
| - // Discard the need for a mutable borrow |
224 |
| - match a.pop() { |
225 |
| - // Extra adjustment made when indexing causes a drop |
226 |
| - // of size information - we need to get rid of it |
227 |
| - // Since this is "after" the other adjustment to be |
228 |
| - // discarded, we do an extra `pop()` |
229 |
| - Some(Adjustment { kind: Adjust::Unsize, .. }) => { |
230 |
| - // So the borrow discard actually happens here |
231 |
| - a.pop(); |
232 |
| - }, |
233 |
| - _ => {} |
234 |
| - } |
235 |
| - }); |
236 |
| - } |
| 197 | + }); |
237 | 198 | }
|
238 | 199 | }
|
239 | 200 | }
|
|
0 commit comments