Skip to content

Commit 87bf9e2

Browse files
committed
Address review comments
1 parent f7d35cc commit 87bf9e2

9 files changed

+52
-109
lines changed

src/librustc_typeck/check/demand.rs

+28-35
Original file line numberDiff line numberDiff line change
@@ -317,7 +317,11 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
317317
_ if self.is_range_literal(expr) => true,
318318
_ => false,
319319
};
320-
let sugg_expr = if needs_parens { format!("({})", src) } else { src };
320+
let sugg_expr = if needs_parens {
321+
format!("({})", src)
322+
} else {
323+
src
324+
};
321325

322326
if let Some(sugg) = self.can_use_as_ref(expr) {
323327
return Some(sugg);
@@ -379,67 +383,56 @@ impl<'a, 'gcx, 'tcx> FnCtxt<'a, 'gcx, 'tcx> {
379383
None
380384
}
381385

382-
// This function checks if the specified expression is a built-in range literal
383-
// (See: librustc/hir/lowering.rs::LoweringContext::lower_expr() )
386+
/// This function checks if the specified expression is a built-in range literal.
387+
/// (See: ``librustc::hir::lowering::LoweringContext::lower_expr()``).
384388
fn is_range_literal(&self, expr: &hir::Expr) -> bool {
385389
use hir::{Path, QPath, ExprKind, TyKind};
386390

387-
// we support `::std::ops::Range` and `::std::core::Range` prefixes
388-
// (via split on "|")
389-
let ops_path = ["{{root}}", "std|core", "ops"];
390-
391+
// We support `::std::ops::Range` and `::core::ops::Range` prefixes
391392
let is_range_path = |path: &Path| {
392-
let ident_names: Vec<_> = path.segments
393-
.iter()
394-
.map(|seg| seg.ident.as_str())
395-
.collect();
396-
397-
if let Some((last, preceding)) = ident_names.split_last() {
398-
last.starts_with("Range") &&
399-
preceding.len() == 3 &&
400-
preceding.iter()
401-
.zip(ops_path.iter())
402-
.all(|(seg, match_seg)| {
403-
match_seg.split("|")
404-
.into_iter()
405-
.any(|ref spl_seg| seg == spl_seg)
406-
})
393+
let mut segs = path.segments.iter()
394+
.map(|seg| seg.ident.as_str());
395+
396+
if let (Some(root), Some(std_core), Some(ops), Some(range), None) =
397+
(segs.next(), segs.next(), segs.next(), segs.next(), segs.next())
398+
{
399+
// "{{root}}" is the equivalent of `::` prefix in Path
400+
root == "{{root}}" && (std_core == "std" || std_core == "core")
401+
&& ops == "ops" && range.starts_with("Range")
407402
} else {
408403
false
409404
}
410405
};
411406

412-
let is_range_struct_snippet = |span: &Span| {
413-
// Tell if expression span snippet looks like an explicit
414-
// Range struct or new() call. This is to allow rejecting
415-
// Ranges constructed with non-literals.
407+
let is_range_literal = |span: &Span| {
408+
// Tell if expression span snippet doesn't look like an explicit
409+
// Range struct or `new()` call. This is to allow inferring
410+
// that this is a range literal.
416411
let source_map = self.tcx.sess.source_map();
417412
let end_point = source_map.end_point(*span);
418413

419414
if let Ok(end_string) = source_map.span_to_snippet(end_point) {
420-
end_string.ends_with("}") || end_string.ends_with(")")
415+
!(end_string.ends_with("}") || end_string.ends_with(")"))
421416
} else {
422417
false
423418
}
424-
425419
};
426420

427421
match expr.node {
428-
// all built-in range literals but `..=` and `..`
429-
// desugar to Structs, `..` desugars to its struct path
422+
// All built-in range literals but `..=` and `..` desugar to Structs
430423
ExprKind::Struct(QPath::Resolved(None, ref path), _, _) |
424+
// `..` desugars to its struct path
431425
ExprKind::Path(QPath::Resolved(None, ref path)) => {
432-
return is_range_path(&path) && !is_range_struct_snippet(&expr.span);
426+
return is_range_path(&path) && is_range_literal(&expr.span);
433427
}
434428

435-
// `..=` desugars into RangeInclusive::new(...)
429+
// `..=` desugars into `::std::ops::RangeInclusive::new(...)`
436430
ExprKind::Call(ref func, _) => {
437431
if let ExprKind::Path(QPath::TypeRelative(ref ty, ref segment)) = func.node {
438432
if let TyKind::Path(QPath::Resolved(None, ref path)) = ty.node {
439-
let calls_new = segment.ident.as_str() == "new";
433+
let call_to_new = segment.ident.as_str() == "new";
440434

441-
return is_range_path(&path) && calls_new &&
442-
!is_range_struct_snippet(&expr.span);
435+
return is_range_path(&path) && is_range_literal(&expr.span) && call_to_new;
443436
}
444437
}
445438
}

src/test/ui/range/issue-54505-no-literals.fixed

-10
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,3 @@
1-
// Copyright 2018 The Rust Project Developers. See the COPYRIGHT
2-
// file at the top-level directory of this distribution and at
3-
// http://rust-lang.org/COPYRIGHT.
4-
//
5-
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6-
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7-
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8-
// option. This file may not be copied, modified, or distributed
9-
// except according to those terms.
10-
111
// run-rustfix
122

133
// Regression test for changes introduced while fixing #54505

src/test/ui/range/issue-54505-no-literals.rs

-10
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,3 @@
1-
// Copyright 2018 The Rust Project Developers. See the COPYRIGHT
2-
// file at the top-level directory of this distribution and at
3-
// http://rust-lang.org/COPYRIGHT.
4-
//
5-
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6-
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7-
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8-
// option. This file may not be copied, modified, or distributed
9-
// except according to those terms.
10-
111
// run-rustfix
122

133
// Regression test for changes introduced while fixing #54505

src/test/ui/range/issue-54505-no-literals.stderr

+12-12
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
error[E0308]: mismatched types
2-
--> $DIR/issue-54505-no-literals.rs:26:16
2+
--> $DIR/issue-54505-no-literals.rs:16:16
33
|
44
LL | take_range(std::ops::Range { start: 0, end: 1 });
55
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -11,7 +11,7 @@ LL | take_range(std::ops::Range { start: 0, end: 1 });
1111
found type `std::ops::Range<{integer}>`
1212

1313
error[E0308]: mismatched types
14-
--> $DIR/issue-54505-no-literals.rs:31:16
14+
--> $DIR/issue-54505-no-literals.rs:21:16
1515
|
1616
LL | take_range(::std::ops::Range { start: 0, end: 1 });
1717
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -23,7 +23,7 @@ LL | take_range(::std::ops::Range { start: 0, end: 1 });
2323
found type `std::ops::Range<{integer}>`
2424

2525
error[E0308]: mismatched types
26-
--> $DIR/issue-54505-no-literals.rs:36:16
26+
--> $DIR/issue-54505-no-literals.rs:26:16
2727
|
2828
LL | take_range(std::ops::RangeFrom { start: 1 });
2929
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -35,7 +35,7 @@ LL | take_range(std::ops::RangeFrom { start: 1 });
3535
found type `std::ops::RangeFrom<{integer}>`
3636

3737
error[E0308]: mismatched types
38-
--> $DIR/issue-54505-no-literals.rs:41:16
38+
--> $DIR/issue-54505-no-literals.rs:31:16
3939
|
4040
LL | take_range(::std::ops::RangeFrom { start: 1 });
4141
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -47,7 +47,7 @@ LL | take_range(::std::ops::RangeFrom { start: 1 });
4747
found type `std::ops::RangeFrom<{integer}>`
4848

4949
error[E0308]: mismatched types
50-
--> $DIR/issue-54505-no-literals.rs:46:16
50+
--> $DIR/issue-54505-no-literals.rs:36:16
5151
|
5252
LL | take_range(std::ops::RangeFull {});
5353
| ^^^^^^^^^^^^^^^^^^^^^^
@@ -59,7 +59,7 @@ LL | take_range(std::ops::RangeFull {});
5959
found type `std::ops::RangeFull`
6060

6161
error[E0308]: mismatched types
62-
--> $DIR/issue-54505-no-literals.rs:51:16
62+
--> $DIR/issue-54505-no-literals.rs:41:16
6363
|
6464
LL | take_range(::std::ops::RangeFull {});
6565
| ^^^^^^^^^^^^^^^^^^^^^^^^
@@ -71,7 +71,7 @@ LL | take_range(::std::ops::RangeFull {});
7171
found type `std::ops::RangeFull`
7272

7373
error[E0308]: mismatched types
74-
--> $DIR/issue-54505-no-literals.rs:56:16
74+
--> $DIR/issue-54505-no-literals.rs:46:16
7575
|
7676
LL | take_range(std::ops::RangeInclusive::new(0, 1));
7777
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -83,7 +83,7 @@ LL | take_range(std::ops::RangeInclusive::new(0, 1));
8383
found type `std::ops::RangeInclusive<{integer}>`
8484

8585
error[E0308]: mismatched types
86-
--> $DIR/issue-54505-no-literals.rs:61:16
86+
--> $DIR/issue-54505-no-literals.rs:51:16
8787
|
8888
LL | take_range(::std::ops::RangeInclusive::new(0, 1));
8989
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -95,7 +95,7 @@ LL | take_range(::std::ops::RangeInclusive::new(0, 1));
9595
found type `std::ops::RangeInclusive<{integer}>`
9696

9797
error[E0308]: mismatched types
98-
--> $DIR/issue-54505-no-literals.rs:66:16
98+
--> $DIR/issue-54505-no-literals.rs:56:16
9999
|
100100
LL | take_range(std::ops::RangeTo { end: 5 });
101101
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -107,7 +107,7 @@ LL | take_range(std::ops::RangeTo { end: 5 });
107107
found type `std::ops::RangeTo<{integer}>`
108108

109109
error[E0308]: mismatched types
110-
--> $DIR/issue-54505-no-literals.rs:71:16
110+
--> $DIR/issue-54505-no-literals.rs:61:16
111111
|
112112
LL | take_range(::std::ops::RangeTo { end: 5 });
113113
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -119,7 +119,7 @@ LL | take_range(::std::ops::RangeTo { end: 5 });
119119
found type `std::ops::RangeTo<{integer}>`
120120

121121
error[E0308]: mismatched types
122-
--> $DIR/issue-54505-no-literals.rs:76:16
122+
--> $DIR/issue-54505-no-literals.rs:66:16
123123
|
124124
LL | take_range(std::ops::RangeToInclusive { end: 5 });
125125
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -131,7 +131,7 @@ LL | take_range(std::ops::RangeToInclusive { end: 5 });
131131
found type `std::ops::RangeToInclusive<{integer}>`
132132

133133
error[E0308]: mismatched types
134-
--> $DIR/issue-54505-no-literals.rs:81:16
134+
--> $DIR/issue-54505-no-literals.rs:71:16
135135
|
136136
LL | take_range(::std::ops::RangeToInclusive { end: 5 });
137137
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

src/test/ui/range/issue-54505-no-std.rs

-10
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,3 @@
1-
// Copyright 2018 The Rust Project Developers. See the COPYRIGHT
2-
// file at the top-level directory of this distribution and at
3-
// http://rust-lang.org/COPYRIGHT.
4-
//
5-
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6-
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7-
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8-
// option. This file may not be copied, modified, or distributed
9-
// except according to those terms.
10-
111
// error-pattern: `#[panic_handler]` function required, but not found
122
// error-pattern: language item required, but not found: `eh_personality`
133

src/test/ui/range/issue-54505-no-std.stderr

+6-6
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ error: `#[panic_handler]` function required, but not found
33
error: language item required, but not found: `eh_personality`
44

55
error[E0308]: mismatched types
6-
--> $DIR/issue-54505-no-std.rs:31:16
6+
--> $DIR/issue-54505-no-std.rs:21:16
77
|
88
LL | take_range(0..1);
99
| ^^^^
@@ -15,7 +15,7 @@ LL | take_range(0..1);
1515
found type `core::ops::Range<{integer}>`
1616

1717
error[E0308]: mismatched types
18-
--> $DIR/issue-54505-no-std.rs:36:16
18+
--> $DIR/issue-54505-no-std.rs:26:16
1919
|
2020
LL | take_range(1..);
2121
| ^^^
@@ -27,7 +27,7 @@ LL | take_range(1..);
2727
found type `core::ops::RangeFrom<{integer}>`
2828

2929
error[E0308]: mismatched types
30-
--> $DIR/issue-54505-no-std.rs:41:16
30+
--> $DIR/issue-54505-no-std.rs:31:16
3131
|
3232
LL | take_range(..);
3333
| ^^
@@ -39,7 +39,7 @@ LL | take_range(..);
3939
found type `core::ops::RangeFull`
4040

4141
error[E0308]: mismatched types
42-
--> $DIR/issue-54505-no-std.rs:46:16
42+
--> $DIR/issue-54505-no-std.rs:36:16
4343
|
4444
LL | take_range(0..=1);
4545
| ^^^^^
@@ -51,7 +51,7 @@ LL | take_range(0..=1);
5151
found type `core::ops::RangeInclusive<{integer}>`
5252

5353
error[E0308]: mismatched types
54-
--> $DIR/issue-54505-no-std.rs:51:16
54+
--> $DIR/issue-54505-no-std.rs:41:16
5555
|
5656
LL | take_range(..5);
5757
| ^^^
@@ -63,7 +63,7 @@ LL | take_range(..5);
6363
found type `core::ops::RangeTo<{integer}>`
6464

6565
error[E0308]: mismatched types
66-
--> $DIR/issue-54505-no-std.rs:56:16
66+
--> $DIR/issue-54505-no-std.rs:46:16
6767
|
6868
LL | take_range(..=42);
6969
| ^^^^^

src/test/ui/range/issue-54505.fixed

-10
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,3 @@
1-
// Copyright 2018 The Rust Project Developers. See the COPYRIGHT
2-
// file at the top-level directory of this distribution and at
3-
// http://rust-lang.org/COPYRIGHT.
4-
//
5-
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6-
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7-
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8-
// option. This file may not be copied, modified, or distributed
9-
// except according to those terms.
10-
111
// run-rustfix
122

133
// Regression test for #54505 - range borrowing suggestion had

src/test/ui/range/issue-54505.rs

-10
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,3 @@
1-
// Copyright 2018 The Rust Project Developers. See the COPYRIGHT
2-
// file at the top-level directory of this distribution and at
3-
// http://rust-lang.org/COPYRIGHT.
4-
//
5-
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6-
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7-
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8-
// option. This file may not be copied, modified, or distributed
9-
// except according to those terms.
10-
111
// run-rustfix
122

133
// Regression test for #54505 - range borrowing suggestion had

src/test/ui/range/issue-54505.stderr

+6-6
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
error[E0308]: mismatched types
2-
--> $DIR/issue-54505.rs:24:16
2+
--> $DIR/issue-54505.rs:14:16
33
|
44
LL | take_range(0..1);
55
| ^^^^
@@ -11,7 +11,7 @@ LL | take_range(0..1);
1111
found type `std::ops::Range<{integer}>`
1212

1313
error[E0308]: mismatched types
14-
--> $DIR/issue-54505.rs:29:16
14+
--> $DIR/issue-54505.rs:19:16
1515
|
1616
LL | take_range(1..);
1717
| ^^^
@@ -23,7 +23,7 @@ LL | take_range(1..);
2323
found type `std::ops::RangeFrom<{integer}>`
2424

2525
error[E0308]: mismatched types
26-
--> $DIR/issue-54505.rs:34:16
26+
--> $DIR/issue-54505.rs:24:16
2727
|
2828
LL | take_range(..);
2929
| ^^
@@ -35,7 +35,7 @@ LL | take_range(..);
3535
found type `std::ops::RangeFull`
3636

3737
error[E0308]: mismatched types
38-
--> $DIR/issue-54505.rs:39:16
38+
--> $DIR/issue-54505.rs:29:16
3939
|
4040
LL | take_range(0..=1);
4141
| ^^^^^
@@ -47,7 +47,7 @@ LL | take_range(0..=1);
4747
found type `std::ops::RangeInclusive<{integer}>`
4848

4949
error[E0308]: mismatched types
50-
--> $DIR/issue-54505.rs:44:16
50+
--> $DIR/issue-54505.rs:34:16
5151
|
5252
LL | take_range(..5);
5353
| ^^^
@@ -59,7 +59,7 @@ LL | take_range(..5);
5959
found type `std::ops::RangeTo<{integer}>`
6060

6161
error[E0308]: mismatched types
62-
--> $DIR/issue-54505.rs:49:16
62+
--> $DIR/issue-54505.rs:39:16
6363
|
6464
LL | take_range(..=42);
6565
| ^^^^^

0 commit comments

Comments
 (0)