aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gcc/rust/backend/rust-compile-context.h8
-rw-r--r--gcc/rust/backend/rust-compile-expr.cc7
-rw-r--r--gcc/rust/backend/rust-compile-implitem.h3
-rw-r--r--gcc/rust/backend/rust-compile-pattern.cc9
-rw-r--r--gcc/rust/backend/rust-compile-pattern.h2
-rw-r--r--gcc/rust/backend/rust-mangle.cc68
-rw-r--r--gcc/rust/backend/rust-mangle.h8
-rw-r--r--gcc/rust/hir/rust-ast-lower-pattern.cc17
-rw-r--r--gcc/rust/hir/rust-ast-lower-pattern.h16
-rw-r--r--gcc/rust/typecheck/rust-hir-type-check-expr.h2
-rw-r--r--gcc/rust/typecheck/rust-hir-type-check-pattern.cc9
-rw-r--r--gcc/rust/typecheck/rust-hir-type-check-pattern.h15
-rw-r--r--gcc/rust/typecheck/rust-tyty.cc3
-rw-r--r--gcc/rust/typecheck/rust-tyty.h2
-rw-r--r--gcc/rust/util/rust-hir-map.h101
-rw-r--r--gcc/testsuite/rust/execute/torture/issue-845.rs47
-rw-r--r--gcc/testsuite/rust/execute/torture/issue-851.rs35
-rw-r--r--gcc/testsuite/rust/execute/torture/match3.rs51
-rw-r--r--gcc/testsuite/rust/execute/torture/operator_overload_11.rs37
-rw-r--r--gcc/testsuite/rust/execute/torture/operator_overload_12.rs31
20 files changed, 352 insertions, 119 deletions
diff --git a/gcc/rust/backend/rust-compile-context.h b/gcc/rust/backend/rust-compile-context.h
index 896d42e..43c23dd 100644
--- a/gcc/rust/backend/rust-compile-context.h
+++ b/gcc/rust/backend/rust-compile-context.h
@@ -310,14 +310,6 @@ public:
return mangler.mangle_item (ty, path, mappings->get_current_crate_name ());
}
- std::string mangle_impl_item (const TyTy::BaseType *self,
- const TyTy::BaseType *ty,
- const std::string &name) const
- {
- return mangler.mangle_impl_item (self, ty, name,
- mappings->get_current_crate_name ());
- }
-
private:
::Backend *backend;
Resolver::Resolver *resolver;
diff --git a/gcc/rust/backend/rust-compile-expr.cc b/gcc/rust/backend/rust-compile-expr.cc
index b77a4d5..5e43f5a 100644
--- a/gcc/rust/backend/rust-compile-expr.cc
+++ b/gcc/rust/backend/rust-compile-expr.cc
@@ -275,19 +275,12 @@ CompileExpr::visit (HIR::MatchExpr &expr)
tree case_label = ctx->get_backend ()->label (
fndecl, "" /* empty creates an artificial label */, arm_locus);
- // not sure if we need to add this to the block or if the CASE_LABEL_EXPR
- // does this implicitly
- //
- // tree case_label_decl_statement
- // = ctx->get_backend ()->label_definition_statement (case_label);
-
// setup the bindings for the block
for (auto &kase_pattern : kase_arm.get_patterns ())
{
tree switch_kase_expr
= CompilePatternCaseLabelExpr::Compile (kase_pattern.get (),
case_label, ctx);
- // ctx->add_statement (case_label_decl_statement);
ctx->add_statement (switch_kase_expr);
CompilePatternBindings::Compile (kase_pattern.get (),
diff --git a/gcc/rust/backend/rust-compile-implitem.h b/gcc/rust/backend/rust-compile-implitem.h
index 7b41226..1da607a 100644
--- a/gcc/rust/backend/rust-compile-implitem.h
+++ b/gcc/rust/backend/rust-compile-implitem.h
@@ -153,8 +153,7 @@ public:
std::string ir_symbol_name
= canonical_path->get () + fntype->subst_as_string ();
- std::string asm_name
- = ctx->mangle_impl_item (self, fntype, function.get_function_name ());
+ std::string asm_name = ctx->mangle_item (fntype, *canonical_path);
tree fndecl
= ctx->get_backend ()->function (compiled_fn_type, ir_symbol_name,
diff --git a/gcc/rust/backend/rust-compile-pattern.cc b/gcc/rust/backend/rust-compile-pattern.cc
index e634dbd..27ee487 100644
--- a/gcc/rust/backend/rust-compile-pattern.cc
+++ b/gcc/rust/backend/rust-compile-pattern.cc
@@ -77,6 +77,15 @@ CompilePatternCaseLabelExpr::visit (HIR::TupleStructPattern &pattern)
CompilePatternCaseLabelExpr::visit (pattern.get_path ());
}
+void
+CompilePatternCaseLabelExpr::visit (HIR::WildcardPattern &pattern)
+{
+ // operand 0 being NULL_TREE signifies this is the default case label see:
+ // tree.def for documentation for CASE_LABEL_EXPR
+ case_label_expr
+ = build_case_label (NULL_TREE, NULL_TREE, associated_case_label);
+}
+
// setup the bindings
void
diff --git a/gcc/rust/backend/rust-compile-pattern.h b/gcc/rust/backend/rust-compile-pattern.h
index e49f75c..b12ea93 100644
--- a/gcc/rust/backend/rust-compile-pattern.h
+++ b/gcc/rust/backend/rust-compile-pattern.h
@@ -40,6 +40,8 @@ public:
void visit (HIR::TupleStructPattern &pattern) override;
+ void visit (HIR::WildcardPattern &pattern) override;
+
private:
CompilePatternCaseLabelExpr (Context *ctx, tree associated_case_label)
: HIRCompileBase (ctx), case_label_expr (error_mark_node),
diff --git a/gcc/rust/backend/rust-mangle.cc b/gcc/rust/backend/rust-mangle.cc
index d0fec0d..26c760e 100644
--- a/gcc/rust/backend/rust-mangle.cc
+++ b/gcc/rust/backend/rust-mangle.cc
@@ -31,6 +31,8 @@ legacy_mangle_name (const std::string &name)
m = "$";
else if (c == '&')
m = "RF";
+ else if (c == '<' || c == '>')
+ m = "..";
else
m.push_back (c);
@@ -71,36 +73,6 @@ legacy_hash (const std::string &fingerprint)
}
static std::string
-legacy_mangle_self (const TyTy::BaseType *self)
-{
- if (self->get_kind () != TyTy::TypeKind::ADT)
- return legacy_mangle_name (self->get_name ());
-
- const TyTy::ADTType *s = static_cast<const TyTy::ADTType *> (self);
- std::string buf = s->get_identifier ();
-
- if (s->has_subsititions_defined ())
- {
- buf += kMangledSubstBegin;
-
- const std::vector<TyTy::SubstitutionParamMapping> &params
- = s->get_substs ();
- for (size_t i = 0; i < params.size (); i++)
- {
- const TyTy::SubstitutionParamMapping &sub = params.at (i);
- buf += sub.as_string ();
-
- if ((i + 1) < params.size ())
- buf += kMangledGenericDelim;
- }
-
- buf += kMangledSubstEnd;
- }
-
- return legacy_mangle_name (buf);
-}
-
-static std::string
v0_tuple_prefix (const TyTy::BaseType *ty)
{
if (ty->is_unit ())
@@ -255,19 +227,6 @@ legacy_mangle_item (const TyTy::BaseType *ty,
+ legacy_mangle_canonical_path (path) + hash_sig + kMangledSymbolDelim;
}
-// FIXME this is a wee bit broken
-static std::string
-legacy_mangle_impl_item (const TyTy::BaseType *self, const TyTy::BaseType *ty,
- const std::string &name, const std::string &crate_name)
-{
- const std::string hash = legacy_hash (ty->as_string ());
- const std::string hash_sig = legacy_mangle_name (hash);
-
- return kMangledSymbolPrefix + legacy_mangle_name (crate_name)
- + legacy_mangle_self (self) + legacy_mangle_name (name) + hash_sig
- + kMangledSymbolDelim;
-}
-
static std::string
v0_mangle_item (const TyTy::BaseType *ty, const Resolver::CanonicalPath &path,
const std::string &crate_name)
@@ -282,13 +241,6 @@ v0_mangle_item (const TyTy::BaseType *ty, const Resolver::CanonicalPath &path,
gcc_unreachable ();
}
-static std::string
-v0_mangle_impl_item (const TyTy::BaseType *self, const TyTy::BaseType *ty,
- const std::string &name, const std::string &crate_name)
-{
- gcc_unreachable ();
-}
-
std::string
Mangler::mangle_item (const TyTy::BaseType *ty,
const Resolver::CanonicalPath &path,
@@ -305,21 +257,5 @@ Mangler::mangle_item (const TyTy::BaseType *ty,
}
}
-std::string
-Mangler::mangle_impl_item (const TyTy::BaseType *self, const TyTy::BaseType *ty,
- const std::string &name,
- const std::string &crate_name) const
-{
- switch (version)
- {
- case Mangler::MangleVersion::LEGACY:
- return legacy_mangle_impl_item (self, ty, name, crate_name);
- case Mangler::MangleVersion::V0:
- return v0_mangle_impl_item (self, ty, name, crate_name);
- default:
- gcc_unreachable ();
- }
-}
-
} // namespace Compile
} // namespace Rust
diff --git a/gcc/rust/backend/rust-mangle.h b/gcc/rust/backend/rust-mangle.h
index 9e77c54..0cc7f76 100644
--- a/gcc/rust/backend/rust-mangle.h
+++ b/gcc/rust/backend/rust-mangle.h
@@ -21,6 +21,7 @@
namespace Rust {
namespace Compile {
+
class Mangler
{
public:
@@ -36,11 +37,6 @@ public:
const Resolver::CanonicalPath &path,
const std::string &crate_name) const;
- std::string mangle_impl_item (const TyTy::BaseType *self,
- const TyTy::BaseType *ty,
- const std::string &name,
- const std::string &crate_name) const;
-
static void set_mangling (int frust_mangling_value)
{
version = static_cast<MangleVersion> (frust_mangling_value);
@@ -49,6 +45,8 @@ public:
private:
static enum MangleVersion version;
};
+
} // namespace Compile
} // namespace Rust
+
#endif // RUST_MANGLE_H
diff --git a/gcc/rust/hir/rust-ast-lower-pattern.cc b/gcc/rust/hir/rust-ast-lower-pattern.cc
index cdad523..4bf3c51 100644
--- a/gcc/rust/hir/rust-ast-lower-pattern.cc
+++ b/gcc/rust/hir/rust-ast-lower-pattern.cc
@@ -23,6 +23,23 @@ namespace Rust {
namespace HIR {
void
+ASTLoweringPattern::visit (AST::IdentifierPattern &pattern)
+{
+ auto crate_num = mappings->get_current_crate ();
+ Analysis::NodeMapping mapping (crate_num, pattern.get_node_id (),
+ mappings->get_next_hir_id (crate_num),
+ UNKNOWN_LOCAL_DEFID);
+
+ std::unique_ptr<Pattern> to_bind;
+ translated
+ = new HIR::IdentifierPattern (mapping, pattern.get_ident (),
+ pattern.get_locus (), pattern.get_is_ref (),
+ pattern.get_is_mut () ? Mutability::Mut
+ : Mutability::Imm,
+ std::move (to_bind));
+}
+
+void
ASTLoweringPattern::visit (AST::PathInExpression &pattern)
{
translated = ASTLowerPathInExpression::translate (&pattern);
diff --git a/gcc/rust/hir/rust-ast-lower-pattern.h b/gcc/rust/hir/rust-ast-lower-pattern.h
index a8c4d9bd..60a3ad1 100644
--- a/gcc/rust/hir/rust-ast-lower-pattern.h
+++ b/gcc/rust/hir/rust-ast-lower-pattern.h
@@ -48,21 +48,7 @@ public:
return resolver.translated;
}
- void visit (AST::IdentifierPattern &pattern) override
- {
- auto crate_num = mappings->get_current_crate ();
- Analysis::NodeMapping mapping (crate_num, pattern.get_node_id (),
- mappings->get_next_hir_id (crate_num),
- UNKNOWN_LOCAL_DEFID);
-
- std::unique_ptr<Pattern> to_bind;
- translated
- = new HIR::IdentifierPattern (mapping, pattern.get_ident (),
- pattern.get_locus (), pattern.get_is_ref (),
- pattern.get_is_mut () ? Mutability::Mut
- : Mutability::Imm,
- std::move (to_bind));
- }
+ void visit (AST::IdentifierPattern &pattern) override;
void visit (AST::PathInExpression &pattern) override;
diff --git a/gcc/rust/typecheck/rust-hir-type-check-expr.h b/gcc/rust/typecheck/rust-hir-type-check-expr.h
index 8de736d..631bc86 100644
--- a/gcc/rust/typecheck/rust-hir-type-check-expr.h
+++ b/gcc/rust/typecheck/rust-hir-type-check-expr.h
@@ -1294,7 +1294,7 @@ public:
for (auto &pattern : kase_arm.get_patterns ())
{
TyTy::BaseType *kase_arm_ty
- = TypeCheckPattern::Resolve (pattern.get ());
+ = TypeCheckPattern::Resolve (pattern.get (), scrutinee_tyty);
TyTy::BaseType *checked_kase = scrutinee_tyty->unify (kase_arm_ty);
if (checked_kase->get_kind () == TyTy::TypeKind::ERROR)
diff --git a/gcc/rust/typecheck/rust-hir-type-check-pattern.cc b/gcc/rust/typecheck/rust-hir-type-check-pattern.cc
index 2b93958..bc66312 100644
--- a/gcc/rust/typecheck/rust-hir-type-check-pattern.cc
+++ b/gcc/rust/typecheck/rust-hir-type-check-pattern.cc
@@ -219,5 +219,14 @@ TypeCheckPattern::visit (HIR::StructPattern &pattern)
}
}
+void
+TypeCheckPattern::visit (HIR::WildcardPattern &pattern)
+{
+ // wildcard patterns within the MatchArm's are simply just the same type as
+ // the parent
+ infered = parent->clone ();
+ infered->set_ref (pattern.get_pattern_mappings ().get_hirid ());
+}
+
} // namespace Resolver
} // namespace Rust
diff --git a/gcc/rust/typecheck/rust-hir-type-check-pattern.h b/gcc/rust/typecheck/rust-hir-type-check-pattern.h
index ac348fb..a5e542d 100644
--- a/gcc/rust/typecheck/rust-hir-type-check-pattern.h
+++ b/gcc/rust/typecheck/rust-hir-type-check-pattern.h
@@ -30,14 +30,14 @@ class TypeCheckPattern : public TypeCheckBase
using Rust::Resolver::TypeCheckBase::visit;
public:
- static TyTy::BaseType *Resolve (HIR::Pattern *pattern)
+ static TyTy::BaseType *Resolve (HIR::Pattern *pattern, TyTy::BaseType *parent)
{
- TypeCheckPattern resolver;
+ TypeCheckPattern resolver (parent);
pattern->accept_vis (resolver);
- // FIXME need to check how we do mappings here
if (resolver.infered == nullptr)
- return new TyTy::ErrorType (1);
+ return new TyTy::ErrorType (
+ pattern->get_pattern_mappings ().get_hirid ());
return resolver.infered;
}
@@ -48,10 +48,15 @@ public:
void visit (HIR::TupleStructPattern &pattern) override;
+ void visit (HIR::WildcardPattern &pattern) override;
+
private:
- TypeCheckPattern () : TypeCheckBase (), infered (nullptr) {}
+ TypeCheckPattern (TyTy::BaseType *parent)
+ : TypeCheckBase (), infered (nullptr), parent (parent)
+ {}
TyTy::BaseType *infered;
+ TyTy::BaseType *parent;
};
} // namespace Resolver
diff --git a/gcc/rust/typecheck/rust-tyty.cc b/gcc/rust/typecheck/rust-tyty.cc
index 25fdfa9..f141a41 100644
--- a/gcc/rust/typecheck/rust-tyty.cc
+++ b/gcc/rust/typecheck/rust-tyty.cc
@@ -822,6 +822,9 @@ ADTType::handle_substitions (SubstitutionArgumentMappings subst_mappings)
for (auto &variant : adt->get_variants ())
{
+ if (variant->is_dataless_variant ())
+ continue;
+
for (auto &field : variant->get_fields ())
{
bool ok = ::Rust::TyTy::handle_substitions (subst_mappings, field);
diff --git a/gcc/rust/typecheck/rust-tyty.h b/gcc/rust/typecheck/rust-tyty.h
index 012e846..40c06a5 100644
--- a/gcc/rust/typecheck/rust-tyty.h
+++ b/gcc/rust/typecheck/rust-tyty.h
@@ -1069,6 +1069,8 @@ public:
HirId get_id () const { return id; }
VariantType get_variant_type () const { return type; }
+ bool is_data_variant () const { return type != VariantType::NUM; }
+ bool is_dataless_variant () const { return type == VariantType::NUM; }
std::string get_identifier () const { return identifier; }
int get_discriminant () const { return discriminant; }
diff --git a/gcc/rust/util/rust-hir-map.h b/gcc/rust/util/rust-hir-map.h
index f1f723b..3ed3d47 100644
--- a/gcc/rust/util/rust-hir-map.h
+++ b/gcc/rust/util/rust-hir-map.h
@@ -41,6 +41,11 @@ public:
MULTIPLY,
DIVIDE,
REMAINDER,
+ BITAND,
+ BITOR,
+ BITXOR,
+ SHL,
+ SHR,
NEGATION,
NOT,
@@ -50,6 +55,11 @@ public:
MUL_ASSIGN,
DIV_ASSIGN,
REM_ASSIGN,
+ BITAND_ASSIGN,
+ BITOR_ASSIGN,
+ BITXOR_ASSIGN,
+ SHL_ASSIGN,
+ SHR_ASSIGN,
DEREF,
@@ -78,6 +88,26 @@ public:
{
return ItemType::REMAINDER;
}
+ else if (item.compare ("bitand") == 0)
+ {
+ return ItemType::BITAND;
+ }
+ else if (item.compare ("bitor") == 0)
+ {
+ return ItemType::BITOR;
+ }
+ else if (item.compare ("bitxor") == 0)
+ {
+ return ItemType::BITXOR;
+ }
+ else if (item.compare ("shl") == 0)
+ {
+ return ItemType::SHL;
+ }
+ else if (item.compare ("shr") == 0)
+ {
+ return ItemType::SHR;
+ }
else if (item.compare ("neg") == 0)
{
return ItemType::NEGATION;
@@ -106,6 +136,26 @@ public:
{
return ItemType::REM_ASSIGN;
}
+ else if (item.compare ("bitand_assign") == 0)
+ {
+ return ItemType::BITAND_ASSIGN;
+ }
+ else if (item.compare ("bitor_assign") == 0)
+ {
+ return ItemType::BITOR_ASSIGN;
+ }
+ else if (item.compare ("bitxor_assign") == 0)
+ {
+ return ItemType::BITXOR_ASSIGN;
+ }
+ else if (item.compare ("shl_assign") == 0)
+ {
+ return ItemType::SHL_ASSIGN;
+ }
+ else if (item.compare ("shr_assign") == 0)
+ {
+ return ItemType::SHR_ASSIGN;
+ }
else if (item.compare ("deref") == 0)
{
return ItemType::DEREF;
@@ -128,6 +178,16 @@ public:
return "div";
case REMAINDER:
return "rem";
+ case BITAND:
+ return "bitand";
+ case BITOR:
+ return "bitor";
+ case BITXOR:
+ return "bitxor";
+ case SHL:
+ return "shl";
+ case SHR:
+ return "shr";
case NEGATION:
return "neg";
case NOT:
@@ -142,11 +202,21 @@ public:
return "div_assign";
case REM_ASSIGN:
return "rem_assign";
+ case BITAND_ASSIGN:
+ return "bitand_assign";
+ case BITOR_ASSIGN:
+ return "bitor_assign";
+ case BITXOR_ASSIGN:
+ return "bitxor_assign";
+ case SHL_ASSIGN:
+ return "shl_assign";
+ case SHR_ASSIGN:
+ return "shr_assign";
case DEREF:
return "deref";
case UNKNOWN:
- break;
+ return "<UNKNOWN>";
}
return "<UNKNOWN>";
}
@@ -165,9 +235,16 @@ public:
return ItemType::DIVIDE;
case ArithmeticOrLogicalOperator::MODULUS:
return ItemType::REMAINDER;
-
- default:
- return ItemType::UNKNOWN;
+ case ArithmeticOrLogicalOperator::BITWISE_AND:
+ return ItemType::BITAND;
+ case ArithmeticOrLogicalOperator::BITWISE_OR:
+ return ItemType::BITOR;
+ case ArithmeticOrLogicalOperator::BITWISE_XOR:
+ return ItemType::BITXOR;
+ case ArithmeticOrLogicalOperator::LEFT_SHIFT:
+ return ItemType::SHL;
+ case ArithmeticOrLogicalOperator::RIGHT_SHIFT:
+ return ItemType::SHR;
}
return ItemType::UNKNOWN;
}
@@ -187,9 +264,16 @@ public:
return ItemType::DIV_ASSIGN;
case ArithmeticOrLogicalOperator::MODULUS:
return ItemType::REM_ASSIGN;
-
- default:
- return ItemType::UNKNOWN;
+ case ArithmeticOrLogicalOperator::BITWISE_AND:
+ return ItemType::BITAND_ASSIGN;
+ case ArithmeticOrLogicalOperator::BITWISE_OR:
+ return ItemType::BITOR_ASSIGN;
+ case ArithmeticOrLogicalOperator::BITWISE_XOR:
+ return ItemType::BITXOR_ASSIGN;
+ case ArithmeticOrLogicalOperator::LEFT_SHIFT:
+ return ItemType::SHL_ASSIGN;
+ case ArithmeticOrLogicalOperator::RIGHT_SHIFT:
+ return ItemType::SHR_ASSIGN;
}
return ItemType::UNKNOWN;
}
@@ -202,9 +286,6 @@ public:
return ItemType::NEGATION;
case NegationOperator::NOT:
return ItemType::NOT;
-
- default:
- return ItemType::UNKNOWN;
}
return ItemType::UNKNOWN;
}
diff --git a/gcc/testsuite/rust/execute/torture/issue-845.rs b/gcc/testsuite/rust/execute/torture/issue-845.rs
new file mode 100644
index 0000000..4c689e3
--- /dev/null
+++ b/gcc/testsuite/rust/execute/torture/issue-845.rs
@@ -0,0 +1,47 @@
+// { dg-output "Foo::bar\n" }
+// { dg-additional-options "-w" }
+extern "C" {
+ fn printf(s: *const i8, ...);
+}
+
+struct Foo {}
+
+trait Bar {
+ fn bar(&self) {
+ unsafe {
+ let _a = "Bar::bar\n\0";
+ let _b = _a as *const str;
+ let _c = _b as *const i8;
+ printf(_c);
+ }
+ }
+}
+
+impl Foo {
+ fn bar(&self) {
+ unsafe {
+ let _a = "Foo::bar\n\0";
+ let _b = _a as *const str;
+ let _c = _b as *const i8;
+ printf(_c);
+ }
+ }
+}
+
+impl Bar for Foo {
+ fn bar(&self) {
+ unsafe {
+ let _a = "<Bar as Foo>::bar\n\0";
+ let _b = _a as *const str;
+ let _c = _b as *const i8;
+ printf(_c);
+ }
+ }
+}
+
+pub fn main() -> i32 {
+ let mut f = Foo {};
+ f.bar();
+
+ 0
+}
diff --git a/gcc/testsuite/rust/execute/torture/issue-851.rs b/gcc/testsuite/rust/execute/torture/issue-851.rs
new file mode 100644
index 0000000..3881c7a
--- /dev/null
+++ b/gcc/testsuite/rust/execute/torture/issue-851.rs
@@ -0,0 +1,35 @@
+/* { dg-output "Result: 123\n" } */
+extern "C" {
+ fn printf(s: *const i8, ...);
+}
+
+enum Foo<T> {
+ A,
+ B(T),
+}
+
+fn inspect(a: Foo<i32>) {
+ match a {
+ Foo::A => unsafe {
+ let a = "A\n\0";
+ let b = a as *const str;
+ let c = b as *const i8;
+
+ printf(c);
+ },
+ Foo::B(x) => unsafe {
+ let a = "Result: %i\n\0";
+ let b = a as *const str;
+ let c = b as *const i8;
+
+ printf(c, x);
+ },
+ }
+}
+
+fn main() -> i32 {
+ let a = Foo::B(123);
+ inspect(a);
+
+ 0
+}
diff --git a/gcc/testsuite/rust/execute/torture/match3.rs b/gcc/testsuite/rust/execute/torture/match3.rs
new file mode 100644
index 0000000..3d1fa0c
--- /dev/null
+++ b/gcc/testsuite/rust/execute/torture/match3.rs
@@ -0,0 +1,51 @@
+// { dg-output "Foo::A\nwildcard\nwildcard\nFoo::D 20 80\n" }
+extern "C" {
+ fn printf(s: *const i8, ...);
+}
+
+enum Foo {
+ A,
+ B,
+ C(char),
+ D { x: i64, y: i64 },
+}
+
+fn inspect(f: Foo) {
+ match f {
+ Foo::A => unsafe {
+ let a = "Foo::A\n\0";
+ let b = a as *const str;
+ let c = b as *const i8;
+
+ printf(c);
+ },
+ Foo::D { x, y } => unsafe {
+ let a = "Foo::D %i %i\n\0";
+ let b = a as *const str;
+ let c = b as *const i8;
+
+ printf(c, x, y);
+ },
+ _ => unsafe {
+ let a = "wildcard\n\0";
+ let b = a as *const str;
+ let c = b as *const i8;
+
+ printf(c);
+ },
+ }
+}
+
+fn main() -> i32 {
+ let a = Foo::A;
+ let b = Foo::B;
+ let c = Foo::C('x');
+ let d = Foo::D { x: 20, y: 80 };
+
+ inspect(a);
+ inspect(b);
+ inspect(c);
+ inspect(d);
+
+ 0
+}
diff --git a/gcc/testsuite/rust/execute/torture/operator_overload_11.rs b/gcc/testsuite/rust/execute/torture/operator_overload_11.rs
new file mode 100644
index 0000000..1919941
--- /dev/null
+++ b/gcc/testsuite/rust/execute/torture/operator_overload_11.rs
@@ -0,0 +1,37 @@
+// { dg-output "1\n" }
+// { dg-additional-options "-w" }
+extern "C" {
+ fn printf(s: *const i8, ...);
+}
+
+#[lang = "bitand"]
+pub trait BitAnd<Rhs = Self> {
+ type Output;
+
+ fn bitand(self, rhs: Rhs) -> Self::Output;
+}
+
+impl BitAnd for i32 {
+ type Output = i32;
+
+ fn bitand(self, other: i32) -> i32 {
+ let res = self & other;
+
+ unsafe {
+ let a = "%i\n\0";
+ let b = a as *const str;
+ let c = b as *const i8;
+
+ printf(c, res);
+ }
+
+ res
+ }
+}
+
+fn main() -> i32 {
+ let a;
+ a = 1 & 1;
+
+ 0
+}
diff --git a/gcc/testsuite/rust/execute/torture/operator_overload_12.rs b/gcc/testsuite/rust/execute/torture/operator_overload_12.rs
new file mode 100644
index 0000000..7433330
--- /dev/null
+++ b/gcc/testsuite/rust/execute/torture/operator_overload_12.rs
@@ -0,0 +1,31 @@
+// { dg-output "1\n" }
+// { dg-additional-options "-w" }
+extern "C" {
+ fn printf(s: *const i8, ...);
+}
+
+#[lang = "bitand_assign"]
+pub trait BitAndAssign<Rhs = Self> {
+ fn bitand_assign(&mut self, rhs: Rhs);
+}
+
+impl BitAndAssign for i32 {
+ fn bitand_assign(&mut self, other: i32) {
+ *self &= other;
+
+ unsafe {
+ let a = "%i\n\0";
+ let b = a as *const str;
+ let c = b as *const i8;
+
+ printf(c, *self);
+ }
+ }
+}
+
+fn main() -> i32 {
+ let mut a = 1;
+ a &= 1;
+
+ 0
+}