From b50aa827a07f398d1a9bd81cc66eebe220006f73 Mon Sep 17 00:00:00 2001 From: Luqman Aden Date: Mon, 29 Apr 2013 17:21:59 -0700 Subject: [PATCH 1/2] librustc: Fix pattern matching on cross crate newtype structs. --- src/librustc/middle/check_match.rs | 2 ++ src/librustc/middle/mem_categorization.rs | 1 + src/librustc/middle/resolve.rs | 1 + src/librustc/middle/trans/_match.rs | 4 ++++ 4 files changed, 8 insertions(+) diff --git a/src/librustc/middle/check_match.rs b/src/librustc/middle/check_match.rs index 9ba1d2523c645..852eb1b50a499 100644 --- a/src/librustc/middle/check_match.rs +++ b/src/librustc/middle/check_match.rs @@ -551,6 +551,8 @@ pub fn specialize(cx: @MatchCheckCtxt, Some(vec::append(args, vec::from_slice(r.tail()))) } def_variant(_, _) => None, + + def_fn(*) | def_struct(*) => { // FIXME #4731: Is this right? --pcw let new_args; diff --git a/src/librustc/middle/mem_categorization.rs b/src/librustc/middle/mem_categorization.rs index 49c5717a357ea..1d0fc7053242b 100644 --- a/src/librustc/middle/mem_categorization.rs +++ b/src/librustc/middle/mem_categorization.rs @@ -915,6 +915,7 @@ pub impl mem_categorization_ctxt { self.cat_pattern(subcmt, *subpat, op); } } + Some(&ast::def_fn(*)) | Some(&ast::def_struct(*)) => { for subpats.each |subpat| { let cmt_field = self.cat_anon_struct_field(*subpat, diff --git a/src/librustc/middle/resolve.rs b/src/librustc/middle/resolve.rs index 5354ffc5d3c82..d56474df2b0f8 100644 --- a/src/librustc/middle/resolve.rs +++ b/src/librustc/middle/resolve.rs @@ -4279,6 +4279,7 @@ pub impl Resolver { pat_enum(path, _) => { // This must be an enum variant, struct or const. match self.resolve_path(path, ValueNS, false, visitor) { + Some(def @ def_fn(*)) | Some(def @ def_variant(*)) | Some(def @ def_struct(*)) | Some(def @ def_const(*)) => { diff --git a/src/librustc/middle/trans/_match.rs b/src/librustc/middle/trans/_match.rs index e31ad63953e05..3755cca8c35e9 100644 --- a/src/librustc/middle/trans/_match.rs +++ b/src/librustc/middle/trans/_match.rs @@ -291,6 +291,7 @@ pub fn variant_opt(bcx: block, pat_id: ast::node_id) } ::core::util::unreachable(); } + ast::def_fn(*) | ast::def_struct(_) => { return lit(UnitLikeStructLit(pat_id)); } @@ -818,6 +819,7 @@ pub fn get_options(bcx: block, m: &[@Match], col: uint) -> ~[Opt] { // This could be one of: a tuple-like enum variant, a // struct-like enum variant, or a struct. match ccx.tcx.def_map.find(&cur.id) { + Some(&ast::def_fn(*)) | Some(&ast::def_variant(*)) => { add_to_set(ccx.tcx, &mut found, variant_opt(bcx, cur.id)); @@ -1011,6 +1013,7 @@ pub fn any_tuple_struct_pat(bcx: block, m: &[@Match], col: uint) -> bool { match pat.node { ast::pat_enum(_, Some(_)) => { match bcx.tcx().def_map.find(&pat.id) { + Some(&ast::def_fn(*)) | Some(&ast::def_struct(*)) => true, _ => false } @@ -1780,6 +1783,7 @@ pub fn bind_irrefutable_pat(bcx: block, } } } + Some(&ast::def_fn(*)) | Some(&ast::def_struct(*)) => { match *sub_pats { None => { From 10f290ef68870e54e6b5bcc75e953210a26b46e9 Mon Sep 17 00:00:00 2001 From: Luqman Aden Date: Mon, 29 Apr 2013 17:34:02 -0700 Subject: [PATCH 2/2] Add test for cross crate newtype struct in match pattern. --- .../cross-crate-newtype-struct-pat.rs | 21 +++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 src/test/run-pass/cross-crate-newtype-struct-pat.rs diff --git a/src/test/run-pass/cross-crate-newtype-struct-pat.rs b/src/test/run-pass/cross-crate-newtype-struct-pat.rs new file mode 100644 index 0000000000000..37d5c5c700bef --- /dev/null +++ b/src/test/run-pass/cross-crate-newtype-struct-pat.rs @@ -0,0 +1,21 @@ +// Copyright 2013 The Rust Project Developers. See the COPYRIGHT +// file at the top-level directory of this distribution and at +// http://rust-lang.org/COPYRIGHT. +// +// Licensed under the Apache License, Version 2.0 or the MIT license +// , at your +// option. This file may not be copied, modified, or distributed +// except according to those terms. + +// xfail-fast +// aux-build:newtype_struct_xc.rs + +extern mod newtype_struct_xc; + +fn main() { + let x = newtype_struct_xc::Au(21); + match x { + newtype_struct_xc::Au(n) => assert_eq!(n, 21) + } +}