diff options
Diffstat (limited to 'gcc/rust/backend/rust-compile-expr.cc')
-rw-r--r-- | gcc/rust/backend/rust-compile-expr.cc | 135 |
1 files changed, 126 insertions, 9 deletions
diff --git a/gcc/rust/backend/rust-compile-expr.cc b/gcc/rust/backend/rust-compile-expr.cc index 427cd32..1048027 100644 --- a/gcc/rust/backend/rust-compile-expr.cc +++ b/gcc/rust/backend/rust-compile-expr.cc @@ -720,10 +720,9 @@ CompileExpr::resolve_method_address (TyTy::FnType *fntype, HirId ref, if (resolved_item != nullptr) { if (!fntype->has_subsititions_defined ()) - return CompileInherentImplItem::Compile (resolved_item, ctx, true); + return CompileInherentImplItem::Compile (resolved_item, ctx); - return CompileInherentImplItem::Compile (resolved_item, ctx, true, - fntype); + return CompileInherentImplItem::Compile (resolved_item, ctx, fntype); } // it might be resolved to a trait item @@ -778,9 +777,9 @@ CompileExpr::resolve_method_address (TyTy::FnType *fntype, HirId ref, HIR::ImplItem *impl_item = candidate.item.impl.impl_item; if (!fntype->has_subsititions_defined ()) - return CompileInherentImplItem::Compile (impl_item, ctx, true); + return CompileInherentImplItem::Compile (impl_item, ctx); - return CompileInherentImplItem::Compile (impl_item, ctx, true, fntype); + return CompileInherentImplItem::Compile (impl_item, ctx, fntype); } } @@ -1226,11 +1225,11 @@ HIRCompileBase::resolve_deref_adjustment (Resolver::Adjustment &adjustment, tree fn_address = error_mark_node; if (!lookup->has_subsititions_defined ()) - fn_address = CompileInherentImplItem::Compile (resolved_item, ctx, true, - nullptr, true, locus); + fn_address = CompileInherentImplItem::Compile (resolved_item, ctx, nullptr, + true, locus); else - fn_address = CompileInherentImplItem::Compile (resolved_item, ctx, true, - lookup, true, locus); + fn_address = CompileInherentImplItem::Compile (resolved_item, ctx, lookup, + true, locus); // does it need a reference to call tree adjusted_argument = expression; @@ -1255,5 +1254,123 @@ HIRCompileBase::resolve_deref_adjustment (Resolver::Adjustment &adjustment, locus); } +void +CompileExpr::visit (HIR::IdentifierExpr &expr) +{ + NodeId ast_node_id = expr.get_mappings ().get_nodeid (); + + bool is_value = false; + NodeId ref_node_id = UNKNOWN_NODEID; + if (ctx->get_resolver ()->lookup_resolved_name (ast_node_id, &ref_node_id)) + { + // these ref_node_ids will resolve to a pattern declaration but we are + // interested in the definition that this refers to get the parent id + Resolver::Definition def; + if (!ctx->get_resolver ()->lookup_definition (ref_node_id, &def)) + { + rust_error_at (expr.get_locus (), + "unknown reference for resolved name"); + return; + } + ref_node_id = def.parent; + is_value = true; + } + else if (!ctx->get_resolver ()->lookup_resolved_type (ast_node_id, + &ref_node_id)) + { + rust_error_at (expr.get_locus (), + "Failed to lookup type reference for node: %s", + expr.as_string ().c_str ()); + return; + } + + if (ref_node_id == UNKNOWN_NODEID) + { + rust_fatal_error (expr.get_locus (), "unresolved IdentifierExpr: %s", + expr.as_string ().c_str ()); + return; + } + + // node back to HIR + HirId ref; + if (!ctx->get_mappings ()->lookup_node_to_hir ( + expr.get_mappings ().get_crate_num (), ref_node_id, &ref)) + { + rust_error_at (expr.get_locus (), "reverse lookup failure"); + return; + } + + TyTy::BaseType *lookup = nullptr; + if (!ctx->get_tyctx ()->lookup_type (ref, &lookup)) + { + rust_fatal_error (expr.get_locus (), + "failed to find type relevant to this context: %s", + expr.get_mappings ().as_string ().c_str ()); + return; + } + + bool is_type_ref = !is_value; + if (is_type_ref) + { + // this might be a case for + // + // struct S; + // + // fn main() { + // let s = S; + // } + + if (lookup->is_unit ()) + { + translated = ctx->get_backend ()->unit_expression (); + return; + } + + // rust actually treats like this an fn call or structs with fields but + // unit structs are just the struct name lets catch it with an is-unit + // check + gcc_unreachable (); + } + + tree fn = NULL_TREE; + Bvariable *var = nullptr; + if (ctx->lookup_const_decl (ref, &translated)) + { + return; + } + else if (ctx->lookup_function_decl (ref, &fn)) + { + translated + = ctx->get_backend ()->function_code_expression (fn, expr.get_locus ()); + } + else if (ctx->lookup_var_decl (ref, &var)) + { + translated = ctx->get_backend ()->var_expression (var, expr.get_locus ()); + } + else if (ctx->lookup_pattern_binding (ref, &translated)) + { + return; + } + else + { + // lets try and query compile it to an item/impl item + HIR::Item *resolved_item = ctx->get_mappings ()->lookup_hir_item ( + expr.get_mappings ().get_crate_num (), ref); + bool is_hir_item = resolved_item != nullptr; + if (!is_hir_item) + { + translated = error_mark_node; + return; + } + + if (!lookup->has_subsititions_defined ()) + translated = CompileItem::compile (resolved_item, ctx, nullptr, true, + expr.get_locus ()); + else + translated = CompileItem::compile (resolved_item, ctx, lookup, true, + expr.get_locus ()); + } +} + } // namespace Compile } // namespace Rust |