Skip to content

Commit edfe267

Browse files
committed
---
yaml --- r: 104701 b: refs/heads/snap-stage3 c: dd3e9d7 h: refs/heads/master i: 104699: 78d65ef v: v3
1 parent a45ec6e commit edfe267

29 files changed

+178
-105
lines changed

[refs]

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
---
22
refs/heads/master: 62f1d68439dcfd509eaca29887afa97f22938373
33
refs/heads/snap-stage1: e33de59e47c5076a89eadeb38f4934f58a3618a6
4-
refs/heads/snap-stage3: a38e14871a38319249497680737033230249cffa
4+
refs/heads/snap-stage3: dd3e9d743d621f2532e6a5e8f7d0c6081ef6159f
55
refs/heads/try: db814977d07bd798feb24f6b74c00800ef458a13
66
refs/tags/release-0.1: 1f5c5126e96c79d22cb7862f75304136e204f105
77
refs/heads/ndm: f3868061cd7988080c30d6d5bf352a5a5fe2460b

branches/snap-stage3/src/librustc/middle/borrowck/gather_loans/gather_moves.rs

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,22 @@ pub fn gather_assignment(bccx: &BorrowckCtxt,
9494
assignee_loan_path,
9595
assignment_id,
9696
assignment_span,
97-
assignee_id);
97+
assignee_id,
98+
false);
99+
}
100+
101+
pub fn gather_move_and_assignment(bccx: &BorrowckCtxt,
102+
move_data: &MoveData,
103+
assignment_id: ast::NodeId,
104+
assignment_span: Span,
105+
assignee_loan_path: @LoanPath,
106+
assignee_id: ast::NodeId) {
107+
move_data.add_assignment(bccx.tcx,
108+
assignee_loan_path,
109+
assignment_id,
110+
assignment_span,
111+
assignee_id,
112+
true);
98113
}
99114

100115
fn check_is_legal_to_move_from(bccx: &BorrowckCtxt,

branches/snap-stage3/src/librustc/middle/borrowck/gather_loans/mod.rs

Lines changed: 29 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -214,20 +214,19 @@ fn gather_loans_in_expr(this: &mut GatherLoanCtxt,
214214
visit::walk_expr(this, ex, ());
215215
}
216216

217-
ast::ExprAssign(l, _) | ast::ExprAssignOp(_, l, _) => {
218-
let l_cmt = this.bccx.cat_expr(l);
219-
match opt_loan_path(l_cmt) {
220-
Some(l_lp) => {
221-
gather_moves::gather_assignment(this.bccx, &this.move_data,
222-
ex.id, ex.span,
223-
l_lp, l.id);
224-
}
225-
None => {
226-
// This can occur with e.g. `*foo() = 5`. In such
227-
// cases, there is no need to check for conflicts
228-
// with moves etc, just ignore.
229-
}
230-
}
217+
ast::ExprAssign(l, _) => {
218+
with_assignee_loan_path(
219+
this.bccx, l,
220+
|lp| gather_moves::gather_assignment(this.bccx, &this.move_data,
221+
ex.id, ex.span, lp, l.id));
222+
visit::walk_expr(this, ex, ());
223+
}
224+
225+
ast::ExprAssignOp(_, l, _) => {
226+
with_assignee_loan_path(
227+
this.bccx, l,
228+
|lp| gather_moves::gather_move_and_assignment(this.bccx, &this.move_data,
229+
ex.id, ex.span, lp, l.id));
231230
visit::walk_expr(this, ex, ());
232231
}
233232

@@ -288,17 +287,10 @@ fn gather_loans_in_expr(this: &mut GatherLoanCtxt,
288287

289288
ast::ExprInlineAsm(ref ia) => {
290289
for &(_, out) in ia.outputs.iter() {
291-
let out_cmt = this.bccx.cat_expr(out);
292-
match opt_loan_path(out_cmt) {
293-
Some(out_lp) => {
294-
gather_moves::gather_assignment(this.bccx, &this.move_data,
295-
ex.id, ex.span,
296-
out_lp, out.id);
297-
}
298-
None => {
299-
// See the comment for ExprAssign.
300-
}
301-
}
290+
with_assignee_loan_path(
291+
this.bccx, out,
292+
|lp| gather_moves::gather_assignment(this.bccx, &this.move_data,
293+
ex.id, ex.span, lp, out.id));
302294
}
303295
visit::walk_expr(this, ex, ());
304296
}
@@ -309,6 +301,18 @@ fn gather_loans_in_expr(this: &mut GatherLoanCtxt,
309301
}
310302
}
311303

304+
fn with_assignee_loan_path(bccx: &BorrowckCtxt, expr: &ast::Expr, op: |@LoanPath|) {
305+
let cmt = bccx.cat_expr(expr);
306+
match opt_loan_path(cmt) {
307+
Some(lp) => op(lp),
308+
None => {
309+
// This can occur with e.g. `*foo() = 5`. In such
310+
// cases, there is no need to check for conflicts
311+
// with moves etc, just ignore.
312+
}
313+
}
314+
}
315+
312316
impl<'a> GatherLoanCtxt<'a> {
313317
pub fn tcx(&self) -> ty::ctxt { self.bccx.tcx }
314318

branches/snap-stage3/src/librustc/middle/borrowck/mod.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -535,7 +535,7 @@ impl BorrowckCtxt {
535535
move_data::Declared => {
536536
self.tcx.sess.span_err(
537537
use_span,
538-
format!("{} of possibly uninitialized value: `{}`",
538+
format!("{} of possibly uninitialized variable: `{}`",
539539
verb,
540540
self.loan_path_to_str(lp)));
541541
}

branches/snap-stage3/src/librustc/middle/borrowck/move_data.rs

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -33,23 +33,25 @@ use util::ppaux::Repr;
3333

3434
pub struct MoveData {
3535
/// Move paths. See section "Move paths" in `doc.rs`.
36-
paths: RefCell<Vec<MovePath> >,
36+
paths: RefCell<Vec<MovePath>>,
3737

3838
/// Cache of loan path to move path index, for easy lookup.
3939
path_map: RefCell<HashMap<@LoanPath, MovePathIndex>>,
4040

4141
/// Each move or uninitialized variable gets an entry here.
42-
moves: RefCell<Vec<Move> >,
42+
moves: RefCell<Vec<Move>>,
4343

4444
/// Assignments to a variable, like `x = foo`. These are assigned
4545
/// bits for dataflow, since we must track them to ensure that
4646
/// immutable variables are assigned at most once along each path.
47-
var_assignments: RefCell<Vec<Assignment> >,
47+
var_assignments: RefCell<Vec<Assignment>>,
4848

4949
/// Assignments to a path, like `x.f = foo`. These are not
5050
/// assigned dataflow bits, but we track them because they still
5151
/// kill move bits.
52-
path_assignments: RefCell<Vec<Assignment> >,
52+
path_assignments: RefCell<Vec<Assignment>>,
53+
54+
/// Assignments to a variable or path, like `x = foo`, but not `x += foo`.
5355
assignee_ids: RefCell<HashSet<ast::NodeId>>,
5456
}
5557

@@ -392,7 +394,8 @@ impl MoveData {
392394
lp: @LoanPath,
393395
assign_id: ast::NodeId,
394396
span: Span,
395-
assignee_id: ast::NodeId) {
397+
assignee_id: ast::NodeId,
398+
is_also_move: bool) {
396399
/*!
397400
* Adds a new record for an assignment to `lp` that occurs at
398401
* location `id` with the given `span`.
@@ -403,7 +406,7 @@ impl MoveData {
403406

404407
let path_index = self.move_path(tcx, lp);
405408

406-
{
409+
if !is_also_move {
407410
let mut assignee_ids = self.assignee_ids.borrow_mut();
408411
assignee_ids.get().insert(assignee_id);
409412
}

branches/snap-stage3/src/librustc/middle/liveness.rs

Lines changed: 8 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -1468,28 +1468,14 @@ impl Liveness {
14681468

14691469
fn check_local(this: &mut Liveness, local: &Local) {
14701470
match local.init {
1471-
Some(_) => {
1472-
this.warn_about_unused_or_dead_vars_in_pat(local.pat);
1473-
}
1474-
None => {
1475-
1476-
// No initializer: the variable might be unused; if not, it
1477-
// should not be live at this point.
1478-
1479-
debug!("check_local() with no initializer");
1480-
this.pat_bindings(local.pat, |ln, var, sp, id| {
1481-
if !this.warn_about_unused(sp, id, ln, var) {
1482-
match this.live_on_exit(ln, var) {
1483-
None => { /* not live: good */ }
1484-
Some(lnk) => {
1485-
this.report_illegal_read(
1486-
local.span, lnk, var,
1487-
PossiblyUninitializedVariable);
1488-
}
1489-
}
1490-
}
1491-
})
1492-
}
1471+
Some(_) => {
1472+
this.warn_about_unused_or_dead_vars_in_pat(local.pat);
1473+
},
1474+
None => {
1475+
this.pat_bindings(local.pat, |ln, var, sp, id| {
1476+
this.warn_about_unused(sp, id, ln, var);
1477+
})
1478+
}
14931479
}
14941480

14951481
visit::walk_local(this, local, ());
@@ -1644,38 +1630,6 @@ impl Liveness {
16441630
}
16451631
}
16461632

1647-
pub fn report_illegal_read(&self,
1648-
chk_span: Span,
1649-
lnk: LiveNodeKind,
1650-
var: Variable,
1651-
rk: ReadKind) {
1652-
let msg = match rk {
1653-
PossiblyUninitializedVariable => "possibly uninitialized \
1654-
variable",
1655-
PossiblyUninitializedField => "possibly uninitialized field",
1656-
MovedValue => "moved value",
1657-
PartiallyMovedValue => "partially moved value"
1658-
};
1659-
let name = self.ir.variable_name(var);
1660-
match lnk {
1661-
FreeVarNode(span) => {
1662-
self.tcx.sess.span_err(
1663-
span,
1664-
format!("capture of {}: `{}`", msg, name));
1665-
}
1666-
ExprNode(span) => {
1667-
self.tcx.sess.span_err(
1668-
span,
1669-
format!("use of {}: `{}`", msg, name));
1670-
}
1671-
ExitNode | VarDefNode(_) => {
1672-
self.tcx.sess.span_bug(
1673-
chk_span,
1674-
format!("illegal reader: {:?}", lnk));
1675-
}
1676-
}
1677-
}
1678-
16791633
pub fn should_warn(&self, var: Variable) -> Option<~str> {
16801634
let name = self.ir.variable_name(var);
16811635
if name.len() == 0 || name[0] == ('_' as u8) { None } else { Some(name) }

branches/snap-stage3/src/libsyntax/codemap.rs

Lines changed: 58 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -221,6 +221,10 @@ impl FileMap {
221221
// UNCHECKED INVARIANT: these offsets must be added in the right
222222
// order and must be in the right places; there is shared knowledge
223223
// about what ends a line between this file and parse.rs
224+
// WARNING: pos param here is the offset relative to start of CodeMap,
225+
// and CodeMap will append a newline when adding a filemap without a newline at the end,
226+
// so the safe way to call this is with value calculated as
227+
// filemap.start_pos + newline_offset_relative_to_the_start_of_filemap.
224228
pub fn next_line(&self, pos: BytePos) {
225229
// the new charpos must be > the last one (or it's the first one).
226230
let mut lines = self.lines.borrow_mut();;
@@ -267,13 +271,21 @@ impl CodeMap {
267271
}
268272
}
269273

270-
pub fn new_filemap(&self, filename: FileName, src: ~str) -> @FileMap {
274+
pub fn new_filemap(&self, filename: FileName, mut src: ~str) -> @FileMap {
271275
let mut files = self.files.borrow_mut();
272276
let start_pos = match files.get().last() {
273277
None => 0,
274278
Some(last) => last.start_pos.to_uint() + last.src.len(),
275279
};
276280

281+
// Append '\n' in case it's not already there.
282+
// This is a workaround to prevent CodeMap.lookup_filemap_idx from accidentally
283+
// overflowing into the next filemap in case the last byte of span is also the last
284+
// byte of filemap, which leads to incorrect results from CodeMap.span_to_*.
285+
if src.len() > 0 && !src.ends_with("\n") {
286+
src.push_char('\n');
287+
}
288+
277289
let filemap = @FileMap {
278290
name: filename,
279291
src: src,
@@ -510,9 +522,9 @@ mod test {
510522
511523
fm1.next_line(BytePos(0));
512524
fm1.next_line(BytePos(12));
513-
fm2.next_line(BytePos(23));
514-
fm3.next_line(BytePos(23));
515-
fm3.next_line(BytePos(33));
525+
fm2.next_line(BytePos(24));
526+
fm3.next_line(BytePos(24));
527+
fm3.next_line(BytePos(34));
516528
517529
cm
518530
}
@@ -526,7 +538,7 @@ mod test {
526538
assert_eq!(fmabp1.fm.name, ~"blork.rs");
527539
assert_eq!(fmabp1.pos, BytePos(22));
528540
529-
let fmabp2 = cm.lookup_byte_offset(BytePos(23));
541+
let fmabp2 = cm.lookup_byte_offset(BytePos(24));
530542
assert_eq!(fmabp2.fm.name, ~"blork2.rs");
531543
assert_eq!(fmabp2.pos, BytePos(0));
532544
}
@@ -539,7 +551,7 @@ mod test {
539551
let cp1 = cm.bytepos_to_file_charpos(BytePos(22));
540552
assert_eq!(cp1, CharPos(22));
541553
542-
let cp2 = cm.bytepos_to_file_charpos(BytePos(23));
554+
let cp2 = cm.bytepos_to_file_charpos(BytePos(24));
543555
assert_eq!(cp2, CharPos(0));
544556
}
545557
@@ -553,7 +565,7 @@ mod test {
553565
assert_eq!(loc1.line, 2);
554566
assert_eq!(loc1.col, CharPos(10));
555567
556-
let loc2 = cm.lookup_char_pos(BytePos(23));
568+
let loc2 = cm.lookup_char_pos(BytePos(24));
557569
assert_eq!(loc2.file.name, ~"blork2.rs");
558570
assert_eq!(loc2.line, 1);
559571
assert_eq!(loc2.col, CharPos(0));
@@ -567,17 +579,17 @@ mod test {
567579
568580
fm1.next_line(BytePos(0));
569581
fm1.next_line(BytePos(22));
570-
fm2.next_line(BytePos(39));
571-
fm2.next_line(BytePos(57));
582+
fm2.next_line(BytePos(40));
583+
fm2.next_line(BytePos(58));
572584
573585
fm1.record_multibyte_char(BytePos(3), 3);
574586
fm1.record_multibyte_char(BytePos(9), 3);
575587
fm1.record_multibyte_char(BytePos(12), 3);
576588
fm1.record_multibyte_char(BytePos(15), 3);
577589
fm1.record_multibyte_char(BytePos(18), 3);
578-
fm2.record_multibyte_char(BytePos(49), 3);
579-
fm2.record_multibyte_char(BytePos(52), 3);
580-
fm2.record_multibyte_char(BytePos(57), 3);
590+
fm2.record_multibyte_char(BytePos(50), 3);
591+
fm2.record_multibyte_char(BytePos(53), 3);
592+
fm2.record_multibyte_char(BytePos(58), 3);
581593
582594
cm
583595
}
@@ -593,10 +605,42 @@ mod test {
593605
let cp2 = cm.bytepos_to_file_charpos(BytePos(6));
594606
assert_eq!(cp2, CharPos(4));
595607
596-
let cp3 = cm.bytepos_to_file_charpos(BytePos(55));
608+
let cp3 = cm.bytepos_to_file_charpos(BytePos(56));
597609
assert_eq!(cp3, CharPos(12));
598610
599-
let cp4 = cm.bytepos_to_file_charpos(BytePos(60));
611+
let cp4 = cm.bytepos_to_file_charpos(BytePos(61));
600612
assert_eq!(cp4, CharPos(15));
601613
}
614+
615+
#[test]
616+
fn t7() {
617+
// Test span_to_lines for a span ending at the end of filemap
618+
let cm = init_code_map();
619+
let span = Span {lo: BytePos(12), hi: BytePos(23), expn_info: None};
620+
let file_lines = cm.span_to_lines(span);
621+
622+
assert_eq!(file_lines.file.name, ~"blork.rs");
623+
assert_eq!(file_lines.lines.len(), 1);
624+
assert_eq!(*file_lines.lines.get(0), 1u);
625+
}
626+
627+
#[test]
628+
fn t8() {
629+
// Test span_to_snippet for a span ending at the end of filemap
630+
let cm = init_code_map();
631+
let span = Span {lo: BytePos(12), hi: BytePos(23), expn_info: None};
632+
let snippet = cm.span_to_snippet(span);
633+
634+
assert_eq!(snippet, Some(~"second line"));
635+
}
636+
637+
#[test]
638+
fn t9() {
639+
// Test span_to_str for a span ending at the end of filemap
640+
let cm = init_code_map();
641+
let span = Span {lo: BytePos(12), hi: BytePos(23), expn_info: None};
642+
let sstr = cm.span_to_str(span);
643+
644+
assert_eq!(sstr, ~"blork.rs:2:1: 2:12");
645+
}
602646
}

branches/snap-stage3/src/test/compile-fail/asm-out-read-uninit.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ fn foo(x: int) { info!("{}", x); }
1919
pub fn main() {
2020
let x: int;
2121
unsafe {
22-
asm!("mov $1, $0" : "=r"(x) : "r"(x)); //~ ERROR use of possibly uninitialized value: `x`
22+
asm!("mov $1, $0" : "=r"(x) : "r"(x)); //~ ERROR use of possibly uninitialized variable: `x`
2323
}
2424
foo(x);
2525
}

0 commit comments

Comments
 (0)