aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPhilip Herron <philip.herron@embecosm.com>2021-09-08 15:01:38 +0100
committerPhilip Herron <philip.herron@embecosm.com>2021-09-08 15:01:38 +0100
commit782cbcdee4047e47ed122d082f51c37db9fdeda2 (patch)
tree4feb3f809c7527598f672fe1da2aa3a2b34464bf
parent8a9271e1921d0eac46bda889da6508cf94d32682 (diff)
downloadgcc-782cbcdee4047e47ed122d082f51c37db9fdeda2.zip
gcc-782cbcdee4047e47ed122d082f51c37db9fdeda2.tar.gz
gcc-782cbcdee4047e47ed122d082f51c37db9fdeda2.tar.bz2
Keep track of the ABI in function types
We need to know the specified ABI in order to determine the linkage, it might be a plain old rust function, an extern C function or a compiler intrinsic and each of these needed to be handled differently.
-rw-r--r--gcc/rust/typecheck/rust-hir-type-check-implitem.h34
-rw-r--r--gcc/rust/typecheck/rust-hir-type-check-stmt.h11
-rw-r--r--gcc/rust/typecheck/rust-hir-type-check-toplevel.h13
-rw-r--r--gcc/rust/typecheck/rust-hir-type-check.cc11
-rw-r--r--gcc/rust/typecheck/rust-tyty.cc2
-rw-r--r--gcc/rust/typecheck/rust-tyty.h50
6 files changed, 87 insertions, 34 deletions
diff --git a/gcc/rust/typecheck/rust-hir-type-check-implitem.h b/gcc/rust/typecheck/rust-hir-type-check-implitem.h
index 59ea4ef..b1eb2e3 100644
--- a/gcc/rust/typecheck/rust-hir-type-check-implitem.h
+++ b/gcc/rust/typecheck/rust-hir-type-check-implitem.h
@@ -33,9 +33,9 @@ class TypeCheckTopLevelExternItem : public TypeCheckBase
using Rust::Resolver::TypeCheckBase::visit;
public:
- static void Resolve (HIR::ExternalItem *item)
+ static void Resolve (HIR::ExternalItem *item, const HIR::ExternBlock &parent)
{
- TypeCheckTopLevelExternItem resolver;
+ TypeCheckTopLevelExternItem resolver (parent);
item->accept_vis (resolver);
}
@@ -115,16 +115,21 @@ public:
if (function.is_variadic ())
flags |= FNTYPE_IS_VARADIC_FLAG;
- auto fnType
- = new TyTy::FnType (function.get_mappings ().get_hirid (),
- function.get_mappings ().get_defid (),
- function.get_item_name (), flags, std::move (params),
- ret_type, std::move (substitutions));
+ auto fnType = new TyTy::FnType (
+ function.get_mappings ().get_hirid (),
+ function.get_mappings ().get_defid (), function.get_item_name (), flags,
+ TyTy::FnType::get_abi_from_string (parent.get_abi (),
+ parent.get_locus ()),
+ std::move (params), ret_type, std::move (substitutions));
context->insert_type (function.get_mappings (), fnType);
}
private:
- TypeCheckTopLevelExternItem () : TypeCheckBase () {}
+ TypeCheckTopLevelExternItem (const HIR::ExternBlock &parent)
+ : TypeCheckBase (), parent (parent)
+ {}
+
+ const HIR::ExternBlock &parent;
};
class TypeCheckTopLevelImplItem : public TypeCheckBase
@@ -233,11 +238,14 @@ public:
context->insert_type (param.get_mappings (), param_tyty);
}
- auto fnType = new TyTy::FnType (
- function.get_mappings ().get_hirid (),
- function.get_mappings ().get_defid (), function.get_function_name (),
- function.is_method () ? FNTYPE_IS_METHOD_FLAG : FNTYPE_DEFAULT_FLAGS,
- std::move (params), ret_type, std::move (substitutions));
+ auto fnType
+ = new TyTy::FnType (function.get_mappings ().get_hirid (),
+ function.get_mappings ().get_defid (),
+ function.get_function_name (),
+ function.is_method () ? FNTYPE_IS_METHOD_FLAG
+ : FNTYPE_DEFAULT_FLAGS,
+ TyTy::FnType::ABI::RUST, std::move (params), ret_type,
+ std::move (substitutions));
context->insert_type (function.get_mappings (), fnType);
}
diff --git a/gcc/rust/typecheck/rust-hir-type-check-stmt.h b/gcc/rust/typecheck/rust-hir-type-check-stmt.h
index 77cbc06..54280e8 100644
--- a/gcc/rust/typecheck/rust-hir-type-check-stmt.h
+++ b/gcc/rust/typecheck/rust-hir-type-check-stmt.h
@@ -329,11 +329,12 @@ public:
context->insert_type (param.get_mappings (), param_tyty);
}
- auto fnType = new TyTy::FnType (function.get_mappings ().get_hirid (),
- function.get_mappings ().get_defid (),
- function.get_function_name (), false,
- std::move (params), ret_type,
- std::move (substitutions));
+ auto fnType
+ = new TyTy::FnType (function.get_mappings ().get_hirid (),
+ function.get_mappings ().get_defid (),
+ function.get_function_name (), FNTYPE_DEFAULT_FLAGS,
+ TyTy::FnType::ABI::RUST, std::move (params), ret_type,
+ std::move (substitutions));
context->insert_type (function.get_mappings (), fnType);
TyTy::FnType *resolved_fn_type = fnType;
diff --git a/gcc/rust/typecheck/rust-hir-type-check-toplevel.h b/gcc/rust/typecheck/rust-hir-type-check-toplevel.h
index 5bffe13..6ec17a9 100644
--- a/gcc/rust/typecheck/rust-hir-type-check-toplevel.h
+++ b/gcc/rust/typecheck/rust-hir-type-check-toplevel.h
@@ -287,11 +287,12 @@ public:
context->insert_type (param.get_mappings (), param_tyty);
}
- auto fnType = new TyTy::FnType (function.get_mappings ().get_hirid (),
- function.get_mappings ().get_defid (),
- function.get_function_name (),
- FNTYPE_DEFAULT_FLAGS, std::move (params),
- ret_type, std::move (substitutions));
+ auto fnType
+ = new TyTy::FnType (function.get_mappings ().get_hirid (),
+ function.get_mappings ().get_defid (),
+ function.get_function_name (), FNTYPE_DEFAULT_FLAGS,
+ TyTy::FnType::ABI::RUST, std::move (params), ret_type,
+ std::move (substitutions));
context->insert_type (function.get_mappings (), fnType);
}
@@ -337,7 +338,7 @@ public:
{
for (auto &item : extern_block.get_extern_items ())
{
- TypeCheckTopLevelExternItem::Resolve (item.get ());
+ TypeCheckTopLevelExternItem::Resolve (item.get (), extern_block);
}
}
diff --git a/gcc/rust/typecheck/rust-hir-type-check.cc b/gcc/rust/typecheck/rust-hir-type-check.cc
index 453f743..bee2748 100644
--- a/gcc/rust/typecheck/rust-hir-type-check.cc
+++ b/gcc/rust/typecheck/rust-hir-type-check.cc
@@ -546,11 +546,12 @@ TraitItemReference::get_type_from_fn (/*const*/ HIR::TraitItemFunc &fn) const
context->insert_type (param.get_mappings (), param_tyty);
}
- auto resolved
- = new TyTy::FnType (fn.get_mappings ().get_hirid (),
- fn.get_mappings ().get_defid (),
- function.get_function_name (), function.is_method (),
- std::move (params), ret_type, substitutions);
+ auto resolved = new TyTy::FnType (
+ fn.get_mappings ().get_hirid (), fn.get_mappings ().get_defid (),
+ function.get_function_name (),
+ function.is_method () ? FNTYPE_IS_METHOD_FLAG : FNTYPE_DEFAULT_FLAGS,
+ TyTy::FnType::ABI::RUST, std::move (params), ret_type, substitutions);
+
context->insert_type (fn.get_mappings (), resolved);
return resolved;
}
diff --git a/gcc/rust/typecheck/rust-tyty.cc b/gcc/rust/typecheck/rust-tyty.cc
index 7eb717f..316caea 100644
--- a/gcc/rust/typecheck/rust-tyty.cc
+++ b/gcc/rust/typecheck/rust-tyty.cc
@@ -882,7 +882,7 @@ FnType::clone () const
std::pair<HIR::Pattern *, BaseType *> (p.first, p.second->clone ()));
return new FnType (get_ref (), get_ty_ref (), get_id (), get_identifier (),
- flags, std::move (cloned_params),
+ flags, abi, std::move (cloned_params),
get_return_type ()->clone (), clone_substs (),
get_combined_refs ());
}
diff --git a/gcc/rust/typecheck/rust-tyty.h b/gcc/rust/typecheck/rust-tyty.h
index 0dfae37..7f149a9 100644
--- a/gcc/rust/typecheck/rust-tyty.h
+++ b/gcc/rust/typecheck/rust-tyty.h
@@ -1071,12 +1071,51 @@ private:
class FnType : public BaseType, public SubstitutionRef
{
public:
+ // FIXME these could be constants
#define FNTYPE_DEFAULT_FLAGS 0x00
#define FNTYPE_IS_METHOD_FLAG 0x01
#define FNTYPE_IS_EXTERN_FLAG 0x02
#define FNTYPE_IS_VARADIC_FLAG 0X04
- FnType (HirId ref, DefId id, std::string identifier, uint8_t flags,
+ enum ABI
+ {
+ UNKNOWN,
+ RUST,
+ INTRINSIC,
+ C,
+ };
+
+ static ABI get_abi_from_string (const std::string &abi, Location locus)
+ {
+ if (abi.compare ("rust") == 0)
+ return ABI::C;
+ else if (abi.compare ("rust-intrinsic") == 0)
+ return ABI::INTRINSIC;
+ else if (abi.compare ("C") == 0)
+ return ABI::C;
+
+ rust_error_at (locus, "unknown abi specified");
+ return ABI::UNKNOWN;
+ }
+
+ static std::string get_string_from_abi (ABI abi)
+ {
+ switch (abi)
+ {
+ case ABI::RUST:
+ return "rust";
+ case ABI::INTRINSIC:
+ return "rust-intrinsic";
+ case ABI::C:
+ return "C";
+
+ case ABI::UNKNOWN:
+ return "unknown";
+ }
+ return "unknown";
+ }
+
+ FnType (HirId ref, DefId id, std::string identifier, uint8_t flags, ABI abi,
std::vector<std::pair<HIR::Pattern *, BaseType *>> params,
BaseType *type, std::vector<SubstitutionParamMapping> subst_refs,
std::set<HirId> refs = std::set<HirId> ())
@@ -1084,14 +1123,14 @@ public:
SubstitutionRef (std::move (subst_refs),
SubstitutionArgumentMappings::error ()),
params (std::move (params)), type (type), flags (flags),
- identifier (identifier), id (id)
+ identifier (identifier), id (id), abi (abi)
{
LocalDefId local_def_id = id & DEF_ID_LOCAL_DEF_MASK;
rust_assert (local_def_id != UNKNOWN_LOCAL_DEFID);
}
FnType (HirId ref, HirId ty_ref, DefId id, std::string identifier,
- uint8_t flags,
+ uint8_t flags, ABI abi,
std::vector<std::pair<HIR::Pattern *, BaseType *>> params,
BaseType *type, std::vector<SubstitutionParamMapping> subst_refs,
std::set<HirId> refs = std::set<HirId> ())
@@ -1099,7 +1138,7 @@ public:
SubstitutionRef (std::move (subst_refs),
SubstitutionArgumentMappings::error ()),
params (params), type (type), flags (flags), identifier (identifier),
- id (id)
+ id (id), abi (abi)
{
LocalDefId local_def_id = id & DEF_ID_LOCAL_DEF_MASK;
rust_assert (local_def_id != UNKNOWN_LOCAL_DEFID);
@@ -1184,12 +1223,15 @@ public:
FnType *
handle_substitions (SubstitutionArgumentMappings mappings) override final;
+ ABI get_abi () const { return abi; }
+
private:
std::vector<std::pair<HIR::Pattern *, BaseType *>> params;
BaseType *type;
uint8_t flags;
std::string identifier;
DefId id;
+ ABI abi;
};
class FnPtr : public BaseType