aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
Diffstat (limited to 'gcc')
-rw-r--r--gcc/rust/backend/rust-compile-context.h8
-rw-r--r--gcc/rust/backend/rust-compile-implitem.h3
-rw-r--r--gcc/rust/backend/rust-mangle.cc68
-rw-r--r--gcc/rust/backend/rust-mangle.h8
-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/operator_overload_11.rs37
-rw-r--r--gcc/testsuite/rust/execute/torture/operator_overload_12.rs31
11 files changed, 252 insertions, 91 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-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-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/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/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
+}