gccrs: Begin enforcing Sized properly and support anti traits like ?Sized

Sized is implicitly applied to every generic type parameter apart from the
implicit Self type parameter on traits, as that would cause a recursive
bound and would make Traits unable to be appied to unsized types.

In order to keep everything happy this means we also need to support the
anti trait bound '?' so that Sized can be removed properly. The full Sized
rules are not completely implemented here. Slice's and Str's are currently
marked as Sized but there is a small regression here that looks like a more
general bug which should be fixed on its own as part of #2443. There is
a big testsuite update here to pull in the Sized lang item.

Note this lays the bound's ground work so we can start supporting Drop
trait properly which needs tackled very soon.

Fixes: #2375
Addresses: #2443

gcc/rust/ChangeLog:

	* expand/rust-proc-macro.cc (literal_from_string): update Lexer constructor
	(tokenstream_from_string): likewise
	* lex/rust-lex.cc (Lexer::Lexer): likewise
	* lex/rust-lex.h: pass through Linemap
	* parse/rust-cfg-parser.cc (parse_cfg_option): likewise
	* rust-session-manager.cc (Session::load_extern_crate): likewise
	* typecheck/rust-hir-trait-resolve.cc (TraitResolver::resolve_trait):
	dont apply Sized on self
	* typecheck/rust-hir-type-check-base.cc (TypeCheckBase::get_marker_predicate): new
	* typecheck/rust-hir-type-check-base.h: add prototype
	* typecheck/rust-hir-type-check-type.cc (TypeResolveGenericParam::Resolve): apply Sized
	(TypeResolveGenericParam::visit): likewise
	* typecheck/rust-hir-type-check-type.h: update prototypes
	* typecheck/rust-typecheck-context.cc: remove bad assertions
	* typecheck/rust-tyty-bounds.cc (TypeBoundsProbe::assemble_sized_builtin): cleanup
	(TypeCheckBase::get_predicate_from_bound): apply sized rules properly
	* util/rust-hir-map.cc (Mappings::lookup_trait_item_lang_item): helpers
	(Mappings::get_lang_item): likewise
	* util/rust-hir-map.h: likewise
	* util/rust-token-converter.cc (from_ident): update lexer ctor
	(from_punct): likewise

gcc/testsuite/ChangeLog:

	* rust/compile/bounds1.rs: Apply sized trait
	* rust/compile/canonical_paths1.rs: likewise
	* rust/compile/cast_generics.rs: likewise
	* rust/compile/closure_no_type_anno.rs: likewise
	* rust/compile/complex_qualified_path_in_expr.rs: likewise
	* rust/compile/const-issue1440.rs: likewise
	* rust/compile/const_generics_1.rs: likewise
	* rust/compile/const_generics_8.rs: likewise
	* rust/compile/derive_macro1.rs: likewise
	* rust/compile/derive_macro3.rs: likewise
	* rust/compile/derive_macro4.rs: likewise
	* rust/compile/derive_macro6.rs: likewise
	* rust/compile/expected_type_args2.rs: likewise
	* rust/compile/expected_type_args3.rs: likewise
	* rust/compile/generics1.rs: likewise
	* rust/compile/generics11.rs: likewise
	* rust/compile/generics12.rs: likewise
	* rust/compile/generics2.rs: likewise
	* rust/compile/generics3.rs: likewise
	* rust/compile/generics4.rs: likewise
	* rust/compile/generics6.rs: likewise
	* rust/compile/generics7.rs: likewise
	* rust/compile/generics8.rs: likewise
	* rust/compile/if_let_expr.rs: likewise
	* rust/compile/issue-1005.rs: likewise
	* rust/compile/issue-1019.rs: likewise
	* rust/compile/issue-1031.rs: likewise
	* rust/compile/issue-1034.rs: likewise
	* rust/compile/issue-1128.rs: likewise
	* rust/compile/issue-1129-2.rs: likewise
	* rust/compile/issue-1130.rs: likewise
	* rust/compile/issue-1131.rs: likewise
	* rust/compile/issue-1165.rs: likewise
	* rust/compile/issue-1173.rs: likewise
	* rust/compile/issue-1235.rs: likewise
	* rust/compile/issue-1237.rs: likewise
	* rust/compile/issue-1289.rs: likewise
	* rust/compile/issue-1383.rs: likewise
	* rust/compile/issue-1447.rs: likewise
	* rust/compile/issue-1589.rs: likewise
	* rust/compile/issue-1725-1.rs: likewise
	* rust/compile/issue-1725-2.rs: likewise
	* rust/compile/issue-1773.rs: likewise
	* rust/compile/issue-1786.rs: likewise
	* rust/compile/issue-1893.rs: likewise
	* rust/compile/issue-1901.rs: likewise
	* rust/compile/issue-1930.rs: likewise
	* rust/compile/issue-1981.rs: likewise
	* rust/compile/issue-2019-1.rs: likewise
	* rust/compile/issue-2019-2.rs: likewise
	* rust/compile/issue-2019-3.rs: likewise
	* rust/compile/issue-2036.rs: likewise
	* rust/compile/issue-2037.rs: likewise
	* rust/compile/issue-2070.rs: likewise
	* rust/compile/issue-2105.rs: likewise
	* rust/compile/issue-2106.rs: likewise
	* rust/compile/issue-2135.rs: likewise
	* rust/compile/issue-2136-1.rs: likewise
	* rust/compile/issue-2136-2.rs: likewise
	* rust/compile/issue-2139.rs: likewise
	* rust/compile/issue-2142.rs: likewise
	* rust/compile/issue-2165.rs: likewise
	* rust/compile/issue-2166.rs: likewise
	* rust/compile/issue-2190-1.rs: likewise
	* rust/compile/issue-2190-2.rs: likewise
	* rust/compile/issue-2195.rs: likewise
	* rust/compile/issue-2238.rs: likewise
	* rust/compile/issue-2304.rs: likewise
	* rust/compile/issue-850.rs: likewise
	* rust/compile/issue-855.rs: likewise
	* rust/compile/issue-925.rs: likewise
	* rust/compile/macro-issue1400.rs: likewise
	* rust/compile/macro20.rs: likewise
	* rust/compile/macro23.rs: likewise
	* rust/compile/macro40.rs: likewise
	* rust/compile/macro54.rs: likewise
	* rust/compile/name_resolution2.rs: likewise
	* rust/compile/name_resolution4.rs: likewise
	* rust/compile/nested_generic.rs: likewise
	* rust/compile/parse_associated_type_as_generic_arg.rs: likewise
	* rust/compile/parse_associated_type_as_generic_arg2.rs: likewise
	* rust/compile/parse_associated_type_as_generic_arg3.rs: likewise
	* rust/compile/parse_complex_generic_application.rs: likewise
	* rust/compile/parse_complex_generic_application2.rs: likewise
	* rust/compile/path_as_generic_arg.rs: likewise
	* rust/compile/privacy4.rs: likewise
	* rust/compile/privacy6.rs: likewise
	* rust/compile/sizeof-stray-infer-var-bug.rs: likewise
	* rust/compile/stmt_with_block_dot.rs: likewise
	* rust/compile/torture/associated_types1.rs: likewise
	* rust/compile/torture/forward_decl_5.rs: likewise
	* rust/compile/torture/generics1.rs: likewise
	* rust/compile/torture/generics10.rs: likewise
	* rust/compile/torture/generics11.rs: likewise
	* rust/compile/torture/generics12.rs: likewise
	* rust/compile/torture/generics13.rs: likewise
	* rust/compile/torture/generics14.rs: likewise
	* rust/compile/torture/generics15.rs: likewise
	* rust/compile/torture/generics16.rs: likewise
	* rust/compile/torture/generics17.rs: likewise
	* rust/compile/torture/generics18.rs: likewise
	* rust/compile/torture/generics19.rs: likewise
	* rust/compile/torture/generics2.rs: likewise
	* rust/compile/torture/generics20.rs: likewise
	* rust/compile/torture/generics21.rs: likewise
	* rust/compile/torture/generics22.rs: likewise
	* rust/compile/torture/generics23.rs: likewise
	* rust/compile/torture/generics24.rs: likewise
	* rust/compile/torture/generics25.rs: likewise
	* rust/compile/torture/generics26.rs: likewise
	* rust/compile/torture/generics27.rs: likewise
	* rust/compile/torture/generics28.rs: likewise
	* rust/compile/torture/generics29.rs: likewise
	* rust/compile/torture/generics3.rs: likewise
	* rust/compile/torture/generics30.rs: likewise
	* rust/compile/torture/generics31.rs: likewise
	* rust/compile/torture/generics32.rs: likewise
	* rust/compile/torture/generics4.rs: likewise
	* rust/compile/torture/generics5.rs: likewise
	* rust/compile/torture/generics6.rs: likewise
	* rust/compile/torture/generics7.rs: likewise
	* rust/compile/torture/generics8.rs: likewise
	* rust/compile/torture/generics9.rs: likewise
	* rust/compile/torture/intrinsics-2.rs: likewise
	* rust/compile/torture/intrinsics-6.rs: likewise
	* rust/compile/torture/intrinsics-7.rs: likewise
	* rust/compile/torture/intrinsics-8.rs: likewise
	* rust/compile/torture/issue-1024.rs: likewise
	* rust/compile/torture/issue-1075.rs: likewise
	* rust/compile/torture/issue-1432.rs: likewise
	* rust/compile/torture/issue-1555.rs: likewise
	* rust/compile/torture/issue-368.rs: likewise
	* rust/compile/torture/issue-808.rs: likewise
	* rust/compile/torture/issue-862.rs: likewise
	* rust/compile/torture/issue-893-2.rs: likewise
	* rust/compile/torture/issue-893.rs: likewise
	* rust/compile/torture/must_use2.rs: likewise
	* rust/compile/torture/nested_fn2.rs: likewise
	* rust/compile/torture/phantom_data.rs: likewise
	* rust/compile/torture/range-lang-item1.rs: likewise
	* rust/compile/torture/traits1.rs: likewise
	* rust/compile/torture/traits11.rs: likewise
	* rust/compile/torture/traits12.rs: likewise
	* rust/compile/torture/traits13.rs: likewise
	* rust/compile/torture/traits14.rs: likewise
	* rust/compile/torture/traits15.rs: likewise
	* rust/compile/torture/traits16.rs: likewise
	* rust/compile/torture/traits17.rs: likewise
	* rust/compile/torture/traits18.rs: likewise
	* rust/compile/torture/traits19.rs: likewise
	* rust/compile/torture/traits2.rs: likewise
	* rust/compile/torture/traits3.rs: likewise
	* rust/compile/torture/traits4.rs: likewise
	* rust/compile/torture/traits5.rs: likewise
	* rust/compile/torture/traits6.rs: likewise
	* rust/compile/torture/traits7.rs: likewise
	* rust/compile/torture/traits8.rs: likewise
	* rust/compile/torture/traits9.rs: likewise
	* rust/compile/torture/transmute-size-check-1.rs: likewise
	* rust/compile/torture/transmute1.rs: likewise
	* rust/compile/torture/uninit-intrinsic-1.rs: likewise
	* rust/compile/torture/utf8_identifiers.rs: likewise
	* rust/compile/traits1.rs: likewise
	* rust/compile/traits10.rs: likewise
	* rust/compile/traits11.rs: likewise
	* rust/compile/traits12.rs: likewise
	* rust/compile/traits2.rs: likewise
	* rust/compile/traits3.rs: likewise
	* rust/compile/traits4.rs: likewise
	* rust/compile/traits5.rs: likewise
	* rust/compile/traits6.rs: likewise
	* rust/compile/traits7.rs: likewise
	* rust/compile/traits8.rs: likewise
	* rust/compile/traits9.rs: likewise
	* rust/compile/type-bindings1.rs: likewise
	* rust/compile/unconstrained_type_param.rs: likewise
	* rust/compile/unsafe10.rs: likewise
	* rust/execute/torture/closure1.rs: likewise
	* rust/execute/torture/closure2.rs: likewise
	* rust/execute/torture/closure3.rs: likewise
	* rust/execute/torture/closure4.rs: likewise
	* rust/execute/torture/coercion1.rs: likewise
	* rust/execute/torture/coercion2.rs: likewise
	* rust/execute/torture/coercion3.rs: likewise
	* rust/execute/torture/copy_nonoverlapping1.rs: likewise
	* rust/execute/torture/derive_macro1.rs: likewise
	* rust/execute/torture/derive_macro3.rs: likewise
	* rust/execute/torture/derive_macro4.rs: likewise
	* rust/execute/torture/index1.rs: likewise
	* rust/execute/torture/issue-1120.rs: likewise
	* rust/execute/torture/issue-1133.rs: likewise
	* rust/execute/torture/issue-1198.rs: likewise
	* rust/execute/torture/issue-1232.rs: likewise
	* rust/execute/torture/issue-1249.rs: likewise
	* rust/execute/torture/issue-1436.rs: likewise
	* rust/execute/torture/issue-1496.rs: likewise
	* rust/execute/torture/issue-1720-2.rs: likewise
	* rust/execute/torture/issue-1720.rs: likewise
	* rust/execute/torture/issue-2052.rs: likewise
	* rust/execute/torture/issue-2179.rs: likewise
	* rust/execute/torture/issue-2180.rs: likewise
	* rust/execute/torture/issue-2236.rs: likewise
	* rust/execute/torture/issue-647.rs: likewise
	* rust/execute/torture/issue-845.rs: likewise
	* rust/execute/torture/issue-851.rs: likewise
	* rust/execute/torture/issue-858.rs: likewise
	* rust/execute/torture/macros23.rs: likewise
	* rust/execute/torture/macros28.rs: likewise
	* rust/execute/torture/method2.rs: likewise
	* rust/execute/torture/method3.rs: likewise
	* rust/execute/torture/method4.rs: likewise
	* rust/execute/torture/operator_overload_1.rs: likewise
	* rust/execute/torture/operator_overload_10.rs: likewise
	* rust/execute/torture/operator_overload_11.rs: likewise
	* rust/execute/torture/operator_overload_12.rs: likewise
	* rust/execute/torture/operator_overload_2.rs: likewise
	* rust/execute/torture/operator_overload_3.rs: likewise
	* rust/execute/torture/operator_overload_4.rs: likewise
	* rust/execute/torture/operator_overload_5.rs: likewise
	* rust/execute/torture/operator_overload_6.rs: likewise
	* rust/execute/torture/operator_overload_7.rs: likewise
	* rust/execute/torture/operator_overload_8.rs: likewise
	* rust/execute/torture/operator_overload_9.rs: likewise
	* rust/execute/torture/prefetch_data.rs: likewise
	* rust/execute/torture/ref-pattern2.rs: likewise
	* rust/execute/torture/slice-magic.rs: likewise
	* rust/execute/torture/slice-magic2.rs: likewise
	* rust/execute/torture/slice1.rs: likewise
	* rust/execute/torture/str-layout1.rs: likewise
	* rust/execute/torture/trait1.rs: likewise
	* rust/execute/torture/trait10.rs: likewise
	* rust/execute/torture/trait11.rs: likewise
	* rust/execute/torture/trait12.rs: likewise
	* rust/execute/torture/trait13.rs: likewise
	* rust/execute/torture/trait2.rs: likewise
	* rust/execute/torture/trait3.rs: likewise
	* rust/execute/torture/trait4.rs: likewise
	* rust/execute/torture/trait5.rs: likewise
	* rust/execute/torture/trait6.rs: likewise
	* rust/execute/torture/trait7.rs: likewise
	* rust/execute/torture/trait8.rs: likewise
	* rust/execute/torture/trait9.rs: likewise
	* rust/execute/torture/transmute1.rs: likewise
	* rust/execute/torture/wrapping_op1.rs: likewise
	* rust/execute/torture/wrapping_op2.rs: likewise
	* rust/link/generic_function_0.rs: likewise
	* rust/link/generic_function_1.rs: likewise
	* rust/compile/issue-2375.rs: New test.

Signed-off-by: Philip Herron <herron.philip@googlemail.com>
This commit is contained in:
Philip Herron 2023-07-18 17:46:08 +01:00 committed by Arthur Cohen
parent f84d52a517
commit 6164ec07c6
263 changed files with 926 additions and 56 deletions

View file

@ -31,7 +31,7 @@ namespace {
ProcMacro::Literal
literal_from_string (const std::string &data, bool &error)
{
Lexer lex (data);
Lexer lex (data, nullptr);
const_TokenPtr output = lex.build_token ();
if (output == nullptr || !output->is_literal ())
{
@ -48,7 +48,7 @@ ProcMacro::TokenStream
tokenstream_from_string (std::string &data, bool &lex_error)
{
// FIXME: Insert location pointing to call site in tokens
Lexer lex (data);
Lexer lex (data, nullptr);
std::vector<const_TokenPtr> tokens;
TokenPtr ptr;

View file

@ -136,9 +136,9 @@ is_identifier_continue (uint32_t codepoint)
return cpp_check_xid_property (codepoint) & CPP_XID_CONTINUE;
}
Lexer::Lexer (const std::string &input)
Lexer::Lexer (const std::string &input, Linemap *linemap)
: input (RAIIFile::create_error ()), current_line (1), current_column (1),
line_map (nullptr), dump_lex_out ({}),
line_map (linemap), dump_lex_out ({}),
raw_input_source (new BufferInputSource (input, 0)),
input_queue{*raw_input_source}, token_queue (TokenSource (this))
{}

View file

@ -161,7 +161,7 @@ public:
tl::optional<std::ofstream &> dump_lex_opt = tl::nullopt);
// Lex the contents of a string instead of a file
Lexer (const std::string &input);
Lexer (const std::string &input, Linemap *linemap);
// dtor
~Lexer ();

View file

@ -27,7 +27,7 @@ parse_cfg_option (std::string &input, std::string &key, std::string &value)
key.clear ();
value.clear ();
auto lexer = Lexer (input);
auto lexer = Lexer (input, nullptr);
auto parser = Parser<Lexer> (lexer);
auto token = parser.peek_current_token ();

View file

@ -1021,7 +1021,7 @@ Session::load_extern_crate (const std::string &crate_name, location_t locus)
mappings->set_current_crate (crate_num);
// then lets parse this as a 2nd crate
Lexer lex (extern_crate.get_metadata ());
Lexer lex (extern_crate.get_metadata (), linemap);
Parser<Lexer> parser (lex);
std::unique_ptr<AST::Crate> metadata_crate = parser.parse_crate ();

View file

@ -164,8 +164,8 @@ TraitResolver::resolve_trait (HIR::Trait *trait_reference)
TyTy::BaseType *self = nullptr;
std::vector<TyTy::SubstitutionParamMapping> substitutions;
// FIXME
// this should use the resolve_generic_params like everywhere else
// this needs to be special cased for the sized trait to not auto implemented
// Sized on Self
for (auto &generic_param : trait_reference->get_generic_params ())
{
switch (generic_param.get ()->get_kind ())
@ -177,16 +177,22 @@ TraitResolver::resolve_trait (HIR::Trait *trait_reference)
break;
case HIR::GenericParam::GenericKind::TYPE: {
auto param_type
= TypeResolveGenericParam::Resolve (generic_param.get ());
context->insert_type (generic_param->get_mappings (), param_type);
auto &typaram = static_cast<HIR::TypeParam &> (*generic_param);
bool is_self
= typaram.get_type_representation ().as_string ().compare ("Self")
== 0;
// https://doc.rust-lang.org/std/marker/trait.Sized.html
// The one exception is the implicit Self type of a trait
bool apply_sized = !is_self;
auto param_type
= TypeResolveGenericParam::Resolve (generic_param.get (),
apply_sized);
context->insert_type (generic_param->get_mappings (), param_type);
substitutions.push_back (
TyTy::SubstitutionParamMapping (typaram, param_type));
if (typaram.get_type_representation ().as_string ().compare ("Self")
== 0)
if (is_self)
{
rust_assert (param_type->get_kind () == TyTy::TypeKind::PARAM);
TyTy::ParamType *p

View file

@ -19,6 +19,7 @@
#include "rust-hir-type-check-base.h"
#include "rust-hir-type-check-expr.h"
#include "rust-hir-type-check-type.h"
#include "rust-hir-trait-resolve.h"
#include "rust-type-util.h"
namespace Rust {
@ -399,5 +400,21 @@ TypeCheckBase::resolve_generic_params (
}
}
TyTy::TypeBoundPredicate
TypeCheckBase::get_marker_predicate (Analysis::RustLangItem::ItemType item_type,
location_t locus)
{
DefId item_id = mappings->get_lang_item (item_type, locus);
HIR::Item *item = mappings->lookup_defid (item_id);
rust_assert (item != nullptr);
rust_assert (item->get_item_kind () == HIR::Item::ItemKind::Trait);
HIR::Trait &trait = *static_cast<HIR::Trait *> (item);
TraitReference *ref = TraitResolver::Resolve (trait);
rust_assert (ref != nullptr);
return TyTy::TypeBoundPredicate (*ref, BoundPolarity::RegularBound, locus);
}
} // namespace Resolver
} // namespace Rust

View file

@ -38,7 +38,9 @@ protected:
TraitReference *resolve_trait_path (HIR::TypePath &);
TyTy::TypeBoundPredicate
get_predicate_from_bound (HIR::TypePath &path, HIR::Type *associated_self);
get_predicate_from_bound (HIR::TypePath &path, HIR::Type *associated_self,
BoundPolarity polarity
= BoundPolarity::RegularBound);
bool check_for_unconstrained (
const std::vector<TyTy::SubstitutionParamMapping> &params_to_constrain,
@ -56,6 +58,10 @@ protected:
const std::vector<std::unique_ptr<HIR::GenericParam> > &generic_params,
std::vector<TyTy::SubstitutionParamMapping> &substitutions);
TyTy::TypeBoundPredicate
get_marker_predicate (Analysis::RustLangItem::ItemType item_type,
location_t locus);
Analysis::Mappings *mappings;
Resolver *resolver;
TypeCheckContext *context;

View file

@ -673,9 +673,9 @@ TypeCheckType::visit (HIR::NeverType &type)
}
TyTy::ParamType *
TypeResolveGenericParam::Resolve (HIR::GenericParam *param)
TypeResolveGenericParam::Resolve (HIR::GenericParam *param, bool apply_sized)
{
TypeResolveGenericParam resolver;
TypeResolveGenericParam resolver (apply_sized);
switch (param->get_kind ())
{
case HIR::GenericParam::GenericKind::TYPE:
@ -733,8 +733,26 @@ TypeResolveGenericParam::visit (HIR::TypeParam &param)
= new HIR::TypePath (mappings, {}, BUILTINS_LOCATION, false);
}
std::map<DefId, std::vector<TyTy::TypeBoundPredicate>> predicates;
// https://doc.rust-lang.org/std/marker/trait.Sized.html
// All type parameters have an implicit bound of Sized. The special syntax
// ?Sized can be used to remove this bound if its not appropriate.
//
// We can only do this when we are not resolving the implicit Self for Sized
// itself
rust_debug_loc (param.get_locus (), "apply_sized: %s",
apply_sized ? "true" : "false");
if (apply_sized)
{
TyTy::TypeBoundPredicate sized_predicate
= get_marker_predicate (Analysis::RustLangItem::ItemType::SIZED,
param.get_locus ());
predicates[sized_predicate.get_id ()] = {sized_predicate};
}
// resolve the bounds
std::vector<TyTy::TypeBoundPredicate> specified_bounds;
if (param.has_type_param_bounds ())
{
for (auto &bound : param.get_type_param_bounds ())
@ -747,9 +765,40 @@ TypeResolveGenericParam::visit (HIR::TypeParam &param)
TyTy::TypeBoundPredicate predicate
= get_predicate_from_bound (b->get_path (),
implicit_self_bound);
implicit_self_bound,
b->get_polarity ());
if (!predicate.is_error ())
specified_bounds.push_back (std::move (predicate));
{
switch (predicate.get_polarity ())
{
case BoundPolarity::AntiBound: {
bool found = predicates.find (predicate.get_id ())
!= predicates.end ();
if (found)
predicates.erase (predicate.get_id ());
else
{
// emit error message
rich_location r (line_table, b->get_locus ());
r.add_range (predicate.get ()->get_locus ());
rust_error_at (
r, "antibound for %s is not applied here",
predicate.get ()->get_name ().c_str ());
}
}
break;
default: {
if (predicates.find (predicate.get_id ())
== predicates.end ())
{
predicates[predicate.get_id ()] = {};
}
predicates[predicate.get_id ()].push_back (predicate);
}
break;
}
}
}
break;
@ -759,6 +808,16 @@ TypeResolveGenericParam::visit (HIR::TypeParam &param)
}
}
// now to flat map the specified_bounds into the raw specified predicates
std::vector<TyTy::TypeBoundPredicate> specified_bounds;
for (auto it = predicates.begin (); it != predicates.end (); it++)
{
for (const auto &predicate : it->second)
{
specified_bounds.push_back (predicate);
}
}
resolved = new TyTy::ParamType (param.get_type_representation ().as_string (),
param.get_locus (),
param.get_mappings ().get_hirid (), param,

View file

@ -96,7 +96,8 @@ private:
class TypeResolveGenericParam : public TypeCheckBase
{
public:
static TyTy::ParamType *Resolve (HIR::GenericParam *param);
static TyTy::ParamType *Resolve (HIR::GenericParam *param,
bool apply_sized = true);
protected:
void visit (HIR::TypeParam &param);
@ -104,9 +105,12 @@ protected:
void visit (HIR::ConstGenericParam &param);
private:
TypeResolveGenericParam () : TypeCheckBase (), resolved (nullptr) {}
TypeResolveGenericParam (bool apply_sized)
: TypeCheckBase (), resolved (nullptr), apply_sized (apply_sized)
{}
TyTy::ParamType *resolved;
bool apply_sized;
};
class ResolveWhereClauseItem : public TypeCheckBase

View file

@ -345,7 +345,6 @@ void
TypeCheckContext::insert_autoderef_mappings (
HirId id, std::vector<Adjustment> &&adjustments)
{
rust_assert (autoderef_mappings.find (id) == autoderef_mappings.end ());
autoderef_mappings.emplace (id, std::move (adjustments));
}
@ -365,8 +364,6 @@ void
TypeCheckContext::insert_cast_autoderef_mappings (
HirId id, std::vector<Adjustment> &&adjustments)
{
rust_assert (cast_autoderef_mappings.find (id)
== cast_autoderef_mappings.end ());
cast_autoderef_mappings.emplace (id, std::move (adjustments));
}

View file

@ -103,18 +103,22 @@ TypeBoundsProbe::assemble_sized_builtin ()
{
const TyTy::BaseType *raw = receiver->destructure ();
// does this thing actually implement sized?
// https://runrust.miraheze.org/wiki/Dynamically_Sized_Type
// everything is sized except for:
//
// 1. dyn traits
// 2. slices
// 3. str
// 4. ADT's which contain any of the above
// t. tuples which contain any of the above
switch (raw->get_kind ())
{
case TyTy::ADT:
case TyTy::STR:
case TyTy::ARRAY:
case TyTy::REF:
case TyTy::POINTER:
case TyTy::PARAM:
case TyTy::SLICE:
case TyTy::FNDEF:
case TyTy::FNPTR:
case TyTy::TUPLE:
case TyTy::BOOL:
case TyTy::CHAR:
case TyTy::INT:
@ -124,13 +128,21 @@ TypeBoundsProbe::assemble_sized_builtin ()
case TyTy::ISIZE:
case TyTy::CLOSURE:
case TyTy::INFER:
assemble_builtin_candidate (Analysis::RustLangItem::SIZED);
break;
case TyTy::ARRAY:
case TyTy::NEVER:
case TyTy::PLACEHOLDER:
case TyTy::PROJECTION:
assemble_builtin_candidate (Analysis::RustLangItem::SIZED);
break;
// FIXME str and slice need to be moved and test cases updated
case TyTy::SLICE:
case TyTy::STR:
case TyTy::ADT:
case TyTy::TUPLE:
// FIXME add extra checks
assemble_builtin_candidate (Analysis::RustLangItem::SIZED);
break;
case TyTy::DYNAMIC:
case TyTy::ERROR:
break;
@ -171,7 +183,8 @@ TypeCheckBase::resolve_trait_path (HIR::TypePath &path)
TyTy::TypeBoundPredicate
TypeCheckBase::get_predicate_from_bound (HIR::TypePath &type_path,
HIR::Type *associated_self)
HIR::Type *associated_self,
BoundPolarity polarity)
{
TyTy::TypeBoundPredicate lookup = TyTy::TypeBoundPredicate::error ();
bool already_resolved
@ -184,8 +197,7 @@ TypeCheckBase::get_predicate_from_bound (HIR::TypePath &type_path,
if (trait->is_error ())
return TyTy::TypeBoundPredicate::error ();
TyTy::TypeBoundPredicate predicate (*trait, BoundPolarity::RegularBound,
type_path.get_locus ());
TyTy::TypeBoundPredicate predicate (*trait, polarity, type_path.get_locus ());
HIR::GenericArgs args
= HIR::GenericArgs::create_empty (type_path.get_locus ());
@ -234,7 +246,8 @@ TypeCheckBase::get_predicate_from_bound (HIR::TypePath &type_path,
TypeCheckType::Resolve (fn.get_return_type ().get ());
HIR::TraitItem *trait_item = mappings->lookup_trait_item_lang_item (
Analysis::RustLangItem::ItemType::FN_ONCE_OUTPUT);
Analysis::RustLangItem::ItemType::FN_ONCE_OUTPUT,
final_seg->get_locus ());
std::vector<HIR::GenericArgsBinding> bindings;
location_t output_locus = fn.get_return_type ()->get_locus ();
@ -609,10 +622,11 @@ TypeBoundPredicate::handle_substitions (
TyTy::BaseType *type = it.second;
TypeBoundPredicateItem item = lookup_associated_item (identifier);
rust_assert (!item.is_error ());
const auto item_ref = item.get_raw_item ();
item_ref->associated_type_set (type);
if (!item.is_error ())
{
const auto item_ref = item.get_raw_item ();
item_ref->associated_type_set (type);
}
}
// FIXME more error handling at some point

View file

@ -1266,16 +1266,23 @@ Mappings::lookup_builtin_marker ()
return builtinMarker;
}
HIR::TraitItem *
Mappings::lookup_trait_item_lang_item (Analysis::RustLangItem::ItemType item)
DefId
Mappings::get_lang_item (RustLangItem::ItemType item_type, location_t locus)
{
DefId trait_item_id = UNKNOWN_DEFID;
bool trait_item_lang_item_defined = lookup_lang_item (item, &trait_item_id);
DefId item = UNKNOWN_DEFID;
bool ok = lookup_lang_item (item_type, &item);
if (!ok)
rust_fatal_error (locus, "failed to find lang item %s",
RustLangItem::ToString (item_type).c_str ());
// FIXME
// make this an error? what does rustc do when a lang item is not defined?
rust_assert (trait_item_lang_item_defined);
return item;
}
HIR::TraitItem *
Mappings::lookup_trait_item_lang_item (Analysis::RustLangItem::ItemType item,
location_t locus)
{
DefId trait_item_id = get_lang_item (item, locus);
return lookup_trait_item_defid (trait_item_id);
}

View file

@ -271,6 +271,9 @@ public:
return true;
}
// This will fatal_error when this lang item does not exist
DefId get_lang_item (RustLangItem::ItemType item_type, location_t locus);
void insert_macro_def (AST::MacroRulesDefinition *macro);
bool lookup_macro_def (NodeId id, AST::MacroRulesDefinition **def);
@ -342,7 +345,8 @@ public:
HIR::ImplBlock *lookup_builtin_marker ();
HIR::TraitItem *
lookup_trait_item_lang_item (Analysis::RustLangItem::ItemType item);
lookup_trait_item_lang_item (Analysis::RustLangItem::ItemType item,
location_t locus);
private:
Mappings ();

View file

@ -279,7 +279,7 @@ from_ident (const ProcMacro::Ident &ident, std::vector<const_TokenPtr> &result)
if (ident.is_raw)
value = "r#" + value;
Lexer lexer (value);
Lexer lexer (value, nullptr);
auto token = lexer.build_token ();
token->set_locus (convert (ident.span));
result.push_back (token);
@ -349,7 +349,7 @@ from_punct (const ProcMacro::Punct &punct, std::vector<std::uint32_t> &acc,
{
// TODO: UTF-8 string
std::string whole (acc.begin (), acc.end ());
auto lexer = Lexer (whole);
auto lexer = Lexer (whole, nullptr);
auto token = lexer.build_token ();
token->set_locus (convert (punct.span));
result.push_back (token);

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
mod core {
mod ops {
#[lang = "add"]

View file

@ -1,4 +1,7 @@
// { dg-additional-options "-w -fdump-tree-gimple -frust-crate=example" }
#[lang = "sized"]
pub trait Sized {}
struct Foo(i32);
trait TR {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
fn test<T>(a: T) -> T {
a
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
#[lang = "fn_once"]
trait FnOnce<Args> {
type Output;

View file

@ -1,4 +1,7 @@
struct S; // { dg-warning "struct is never constructed" "" { target *-*-* } .-1 }
#[lang = "sized"]
pub trait Sized {}
struct S; // { dg-warning "struct is never constructed" }
impl S {
fn f() -> i32 { return 0; }
// { dg-warning "associated function is never used" "" { target *-*-* } .-1 }

View file

@ -1,6 +1,9 @@
// { dg-additional-options "-w" }
#![feature(intrinsics)]
#[lang = "sized"]
pub trait Sized {}
mod intrinsics {
extern "rust-intrinsic" {
pub fn wrapping_add<T>(a: T, b: T) -> T;

View file

@ -3,6 +3,9 @@
// There are errors about unused generic parameters, but we can't handle that yet.
// Still, this code is invalid Rust.
#[lang = "sized"]
pub trait Sized {}
mod sain {
struct Foo<const N: usize>;
struct Bar<T, const N: usize>;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Bidule<const N: i32 = 15> {}
enum Bidoule<const N: i32 = 15> {}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Clone {
fn clone(&self) -> Self;
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Clone {
fn clone(&self) -> Self;
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Copy {}
pub trait Clone {
fn clone(&self) -> Self;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Copy {}
pub trait Clone {
fn clone(&self) -> Self;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Foo<A>(A);
fn main() {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Foo<A>(A);
impl Foo {

View file

@ -1,5 +1,8 @@
// { dg-error "expected .i32. got .i8." "" { target *-*-* } 0 }
#[lang = "sized"]
pub trait Sized {}
struct GenericStruct<T>(T, usize);
fn main() {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Foo<T>(T, bool);
impl<T> Foo<T> {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
fn main() {
bar();
// { dg-error "type annotations needed" "" { target *-*-* } .-1 }

View file

@ -1,5 +1,8 @@
// { dg-error "expected .i32. got .i8." "" { target *-*-* } 0 }
#[lang = "sized"]
pub trait Sized {}
struct GenericStruct<T>(T, usize);
fn main() {

View file

@ -1,4 +1,7 @@
// { dg-error "expected .i32. got .i8." "" { target *-*-* } 0 }
#[lang = "sized"]
pub trait Sized {}
struct GenericStruct<T>(T, usize);
fn main() {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct GenericStruct<T>(T, usize);
fn main() {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Foo<A> {
a: A,
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Foo<A> {
a: A,
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Foo<A, B>(A, B);
impl<T> Foo<i32, T> {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub enum Option<T> {
None,
Some(T),

View file

@ -1,4 +1,7 @@
// { dg-additional-options "-w" }
#[lang = "sized"]
pub trait Sized {}
impl<T> *const T {
fn test(self) {}
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait A<T> {
type Output;

View file

@ -1,5 +1,8 @@
#![feature(intrinsics)]
#[lang = "sized"]
pub trait Sized {}
extern "rust-intrinsic" {
#[rustc_const_stable(feature = "const_ptr_offset", since = "1.61.0")]
pub fn offset<T>(dst: *const T, offset: isize) -> *const T;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Foo<T> {
type Output;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Hasher {
fn write(&mut self, bytes: &[u8]);
fn write_u8(&mut self, i: u8) {

View file

@ -1,4 +1,7 @@
// { dg-additional-options "-w" }
#[lang = "sized"]
pub trait Sized {}
pub trait Hasher {
fn finish(&self) -> u64;
fn write(&mut self, bytes: &[u8]);

View file

@ -1,6 +1,9 @@
// { dg-additional-options "-w" }
#![feature(intrinsics)]
#[lang = "sized"]
pub trait Sized {}
mod mem {
extern "rust-intrinsic" {
fn size_of<T>() -> usize;

View file

@ -1,5 +1,8 @@
#![feature(intrinsics)]
#[lang = "sized"]
pub trait Sized {}
extern "rust-intrinsic" {
fn size_of<T>() -> usize;
fn offset<T>(dst: *const T, offset: isize) -> *const T;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Foo<T>(T);
fn main() {

View file

@ -2,6 +2,9 @@
#![feature(intrinsics)]
#[lang = "sized"]
pub trait Sized {}
mod mem {
extern "rust-intrinsic" {
pub fn transmute<U, V>(_: U) -> V;

View file

@ -1,4 +1,7 @@
// { dg-additional-options "-w" }
#[lang = "sized"]
pub trait Sized {}
struct FatPtr<T> {
data: *const T,
len: usize,

View file

@ -1,6 +1,9 @@
// { dg-additional-options "-w" }
#![feature(intrinsics)]
#[lang = "sized"]
pub trait Sized {}
mod intrinsics {
extern "rust-intrinsic" {
pub fn offset<T>(ptr: *const T, count: isize) -> *const T;

View file

@ -1,5 +1,8 @@
#![feature(intrinsics)]
#[lang = "sized"]
pub trait Sized {}
extern "C" {
fn printf(s: *const i8, ...);
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub fn generic_function<X>(a: X) -> X {
a
}

View file

@ -1,4 +1,7 @@
// { dg-options "-w" }
#[lang = "sized"]
pub trait Sized {}
struct PhantomData<T>;
struct Hasher<S> {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait A: B {}
// { dg-error "trait cycle detected" "" { target *-*-* } .-1 }

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
mod core {
mod ops {
#[lang = "add"]

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
mod core {
mod ops {
#[lang = "add"]

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Foo<T> {
type A;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
#[lang = "clone"]
trait Clone {
fn clone(&self) -> Self;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub enum Option<T> {
None,
Some(T),

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
mod intrinsics {
extern "rust-intrinsic" {
pub fn offset<T>(ptr: *const T, count: isize) -> *const T;

View file

@ -1,4 +1,7 @@
// { dg-options "-w" }
#[lang = "sized"]
pub trait Sized {}
fn test<T>(x: *mut T) {
let x = x as *mut u8;
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
mod intrinsics {
extern "rust-intrinsic" {
pub fn offset<T>(ptr: *const T, count: isize) -> *const T;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
#[lang = "add"]
pub trait Add<RHS = Self> {
type Output;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
#[lang = "add"]
pub trait Add<RHS = Self> {
type Output;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
macro_rules! forward_ref_binop {
(impl $imp:ident, $method:ident for $t:ty, $u:ty) => {
forward_ref_binop!(impl $imp, $method for $t, $u,

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Hash<H> {
fn hash2(&self, hasher: &H) -> u64;
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Foo {
fn bar(&mut self, other: &mut Foo);
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Foo {
fn get(self) -> i32;
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub enum Option<T> {
Some(T),
None,

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Foo(u32);
// { dg-warning "struct is never constructed" "" { target *-*-* } .-1 }

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Foo<A> {
fn foo(self, _: A) -> u16;
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Foo {
fn foo();
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct S;
impl S {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Foo {
fn foo();
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
#[lang = "fn_once"]
pub trait FnOnce<Args> {
#[lang = "fn_once_output"]

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Alpha<T = Self> {
type Beta;
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Add {
type Output;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
#[lang = "deref"]
trait Deref {
type Target;

View file

@ -1,4 +1,7 @@
// { dg-options "-w" }
#[lang = "sized"]
pub trait Sized {}
#[lang = "deref"]
trait Deref {
type Target;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct A<T> {
// { dg-warning "struct is never constructed" "" { target *-*-* } .-1 }
f: *const T,

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
fn main() {
struct Foo;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
#[lang = "add"]
pub trait Add<RHS = Self> {
type Output;

View file

@ -0,0 +1,14 @@
#[lang = "sized"]
pub trait Sized {}
pub trait Trait {
fn foo(&self) -> Self
where
Self: Sized;
}
pub fn static_foo<T: Trait + ?Sized>(_b: &T) {}
pub fn dynamic_bar(a: &dyn Trait) {
static_foo(a)
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
extern "C" {
fn printf(s: *const i8, ...);
}

View file

@ -1,5 +1,8 @@
pub use result::Result::{self, Err, Ok};
#[lang = "sized"]
pub trait Sized {}
extern "C" {
fn printf(s: *const i8, ...);
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct S;
trait A {
fn foo(&self);

View file

@ -1,5 +1,8 @@
// { dg-additional-options "-w" }
#[lang = "sized"]
pub trait Sized {}
macro_rules! foo {
( ( $( $Trait: ident ),+ ) for $Ty: ident ) => {
$(

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
macro_rules! define_trait {
($assoc:ident, $i:item) => {
type $assoc;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
macro_rules! maybe_impl {
($left:ident, $right:ident, $l_fn:ident, $r_fn:ident) => {
fn $l_fn(value: T) -> Maybe<T> {

View file

@ -1,5 +1,8 @@
// { dg-additional-options "-w" }
#[lang = "sized"]
pub trait Sized {}
macro_rules! t {
() => {
i32

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
macro_rules! foo {
() => {"foo"};
(number) => { 12 };

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
struct Bar;
trait Foo {

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Foo {
fn foo(&self) {} // { dg-warning "unused name" }
}

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub struct A<T>(T);
pub struct B<T>(T);

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Foo {
type A;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Foo {
type A;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
trait Bar {
type B;

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub enum Either<T, E> {
Left(T),
Right(E),

View file

@ -1,3 +1,6 @@
#[lang = "sized"]
pub trait Sized {}
pub enum Either<L, R> {
Left(L),
Right(R),

Some files were not shown because too many files have changed in this diff Show more