From patchwork Tue Feb 21 12:01:44 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Arthur Cohen X-Patchwork-Id: 60004 Return-Path: Delivered-To: ouuuleilei@gmail.com Received: by 2002:adf:eb09:0:0:0:0:0 with SMTP id s9csp1834556wrn; Tue, 21 Feb 2023 04:32:02 -0800 (PST) X-Google-Smtp-Source: AK7set+oBg7kxxOUctzYj7vYR8ZZYhwz37QtxFpJxHc6lyB3x95fdtvs7ZLBC6Vm5L5JRC+SLM3I X-Received: by 2002:a17:906:2993:b0:881:23a:aba5 with SMTP id x19-20020a170906299300b00881023aaba5mr10948478eje.11.1676982722483; Tue, 21 Feb 2023 04:32:02 -0800 (PST) ARC-Seal: i=1; a=rsa-sha256; t=1676982722; cv=none; d=google.com; s=arc-20160816; b=RfwrmahzjAJQGw6/MILDfN301Cv3/RaJGEWOEhs8pLlhK8LCRwlRvf4MVEHU6Bz5xF 1ho5NJKLjSQb6DOrUBqAF87ZQTMi50O+sWzqBeHm6sct0B9oRT98Scu/FbcS1FGApDyC 6fsyT14BIXm7F9fDA8F6b+QZZHe+dLAOcKPSx70Gu3albrHrUnFeX575ePUyJbkJ+eMM gomAfYxse/tAXWOrMZ2SK57S3zQMiTHx6Qbnah6xLMOF9kaWFBnMTy6QDX2wSkSrkZDp AUx0iHnAH9xDdLjM07j+rKIL2B2nnYi6wiU85T9sCvFA1dNnb6Ge96ybokQDC4Ad6iRE 2FFg== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=sender:errors-to:reply-to:list-subscribe:list-help:list-post :list-archive:list-unsubscribe:list-id:precedence :content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:dkim-signature:dmarc-filter :delivered-to; bh=DyIW1+oDgSzhRnE28nbxqnk8ukPdAgXqz5DDTys8nMk=; b=aqjCU15gNh03Pk5Fjz8OcVK1d8KCbyHeSXa0m3HvWTHm21/sWCc8dxM5PaweHja061 RQbFMgR++K6WloIBv8wSITCyqaFHC7ad8I0E8o3DBNePec5FM8NfV1WXrlDH1oKlalhP akN6wJmlIb08OVCTv72VxYjxw5qzzz5SJRasnQDE9hDY5Wm1qYLxBvHKu/idOZrmI8X+ Lq9WpRYVS3U06ZipXwygFyGLWRGSHgDQSGaN/9r5qbr/mUkVXF0CXD15CWx+Bo29CbrK VyT4F0fv9di1cAWhR+Y5OXc6glurkGjVZWMaMOtubQwmmfVJKel3bJaiz/26fp8gj6/N esDA== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@embecosm.com header.s=google header.b=Ud25AQqg; spf=pass (google.com: domain of gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org designates 8.43.85.97 as permitted sender) smtp.mailfrom="gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org" Received: from sourceware.org (server2.sourceware.org. [8.43.85.97]) by mx.google.com with ESMTPS id f4-20020a1709063f4400b008b1737316cdsi18227675ejj.720.2023.02.21.04.32.02 for (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 21 Feb 2023 04:32:02 -0800 (PST) Received-SPF: pass (google.com: domain of gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org designates 8.43.85.97 as permitted sender) client-ip=8.43.85.97; Authentication-Results: mx.google.com; dkim=pass header.i=@embecosm.com header.s=google header.b=Ud25AQqg; spf=pass (google.com: domain of gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org designates 8.43.85.97 as permitted sender) smtp.mailfrom="gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org" Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id 228EE38883FC for ; Tue, 21 Feb 2023 12:11:52 +0000 (GMT) X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from mail-wr1-x436.google.com (mail-wr1-x436.google.com [IPv6:2a00:1450:4864:20::436]) by sourceware.org (Postfix) with ESMTPS id 95868383D98B for ; Tue, 21 Feb 2023 12:04:07 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org 95868383D98B Authentication-Results: sourceware.org; dmarc=none (p=none dis=none) header.from=embecosm.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=embecosm.com Received: by mail-wr1-x436.google.com with SMTP id z8so3884159wrm.8 for ; Tue, 21 Feb 2023 04:04:07 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=embecosm.com; s=google; h=content-transfer-encoding:mime-version:reply-to:references :in-reply-to:message-id:date:subject:cc:to:from:from:to:cc:subject :date:message-id:reply-to; bh=DyIW1+oDgSzhRnE28nbxqnk8ukPdAgXqz5DDTys8nMk=; b=Ud25AQqgQELrw5eXsswMcECfu7QsI/hmeN1LYbXukfIXEktJAnfL/9yD2KOnTaq3pZ pdLHX1wh+8Vhai9Btb7jz4b29LKlH1WjbspQG0fyYVR0G2NZH+4yBfvzbrxbf+mYO2eI vRZJlNsdNWTcyKWX6/vZatiseIxclh7sWUqIYvQ1Hye49NOpvQKJrmv5ciXDn5JYGQf6 o2X2lxvyH+slWI78bCLSuVcBBPJFsmgjZtzgPI2YKk2WODs3nEKnzCKDyhT5c1Bedr6B lV3kQA6WZlj2odduVN/nq8spc7NmIwW03IkjIRY9orymagUIWOccov+TkzKOWQvwGM7I Ke8w== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=content-transfer-encoding:mime-version:reply-to:references :in-reply-to:message-id:date:subject:cc:to:from:x-gm-message-state :from:to:cc:subject:date:message-id:reply-to; bh=DyIW1+oDgSzhRnE28nbxqnk8ukPdAgXqz5DDTys8nMk=; b=6k6Pbbksgan7YBc6uH8bKPaZC47PCstDQ98yvx1K3jJY+tChR09bAuGA+e0kO+b5gN 5dFs9wmSnswcB/1BeRCOEWYffaLsn1hkU04bsknxanKGGhEixVypxvGWFxYSRg9CJg8s jZvYtFSdCk8ncRJ1Uaso5gJC/oLGrsACO7YwG3LZSZMf7oi4lcVsfCaUrV1wKoZRgfVV o2bpo5pcUIRNoTL1AQitlFI0JpvpNAQTAY+Shv1q/mNov0O/Ln1AOuoLhyyV0C4x4moi KUHKNqf4G60FzPOneT8FCXABvVul52u2Js+vul80z5wQt08uV4U4TGjih7p+9Z7LXwzL rbHw== X-Gm-Message-State: AO0yUKWJK2ixScVyVUP1zr07vj2xHe5rJNKsBnwHSIaW3jyZUTDGqVVg fXRJcsRpiUdh5lPSp8xufZBN0PaYvia2OYCwqA== X-Received: by 2002:a5d:5306:0:b0:2c5:588f:c5c4 with SMTP id e6-20020a5d5306000000b002c5588fc5c4mr2804459wrv.37.1676981046911; Tue, 21 Feb 2023 04:04:06 -0800 (PST) Received: from platypus.localdomain ([62.23.166.218]) by smtp.gmail.com with ESMTPSA id c15-20020adffb4f000000b002c55b0e6ef1sm5013811wrs.4.2023.02.21.04.04.06 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 21 Feb 2023 04:04:06 -0800 (PST) From: arthur.cohen@embecosm.com To: gcc-patches@gcc.gnu.org Cc: gcc-rust@gcc.gnu.org, Philip Herron Subject: [committed 054/103] gccrs: Support Closure calls as generic trait bounds Date: Tue, 21 Feb 2023 13:01:44 +0100 Message-Id: <20230221120230.596966-55-arthur.cohen@embecosm.com> X-Mailer: git-send-email 2.39.1 In-Reply-To: <20230221120230.596966-1-arthur.cohen@embecosm.com> References: <20230221120230.596966-1-arthur.cohen@embecosm.com> MIME-Version: 1.0 X-Spam-Status: No, score=-14.3 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, RCVD_IN_DNSWL_NONE, SPF_HELO_NONE, SPF_PASS, TXREP autolearn=unavailable autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Reply-To: arthur.cohen@embecosm.com Errors-To: gcc-patches-bounces+ouuuleilei=gmail.com@gcc.gnu.org Sender: "Gcc-patches" X-getmail-retrieved-from-mailbox: =?utf-8?q?INBOX?= X-GMAIL-THRID: =?utf-8?q?1758443834933792209?= X-GMAIL-MSGID: =?utf-8?q?1758443834933792209?= From: Philip Herron gcc/rust/ChangeLog: * backend/rust-compile-expr.cc (CompileExpr::visit): Refactor checking of closures. (CompileExpr::generate_possible_fn_trait_call): New function. * backend/rust-compile-expr.h: Declare `generate_possible_fn_trait_call`. gcc/testsuite/ChangeLog: * rust/execute/torture/closure2.rs: New test. --- gcc/rust/backend/rust-compile-expr.cc | 116 +++++++++++------- gcc/rust/backend/rust-compile-expr.h | 3 + .../rust/execute/torture/closure2.rs | 32 +++++ 3 files changed, 104 insertions(+), 47 deletions(-) create mode 100644 gcc/testsuite/rust/execute/torture/closure2.rs diff --git a/gcc/rust/backend/rust-compile-expr.cc b/gcc/rust/backend/rust-compile-expr.cc index d2d9ae0a233..8169ba02b84 100644 --- a/gcc/rust/backend/rust-compile-expr.cc +++ b/gcc/rust/backend/rust-compile-expr.cc @@ -1693,53 +1693,10 @@ CompileExpr::visit (HIR::CallExpr &expr) auto fn_address = CompileExpr::Compile (expr.get_fnexpr (), ctx); // is this a closure call? - if (RS_CLOSURE_TYPE_P (TREE_TYPE (fn_address))) - { - rust_assert (tyty->get_kind () == TyTy::TypeKind::CLOSURE); - TyTy::ClosureType *closure = static_cast (tyty); - - std::vector tuple_arg_vals; - for (auto &argument : expr.get_arguments ()) - { - auto rvalue = CompileExpr::Compile (argument.get (), ctx); - tuple_arg_vals.push_back (rvalue); - } - - tree tuple_args_tyty - = TyTyResolveCompile::compile (ctx, &closure->get_parameters ()); - tree tuple_args - = ctx->get_backend ()->constructor_expression (tuple_args_tyty, false, - tuple_arg_vals, -1, - expr.get_locus ()); - - // need to apply any autoderef's to the self argument - HirId autoderef_mappings_id = expr.get_mappings ().get_hirid (); - std::vector *adjustments = nullptr; - bool ok - = ctx->get_tyctx ()->lookup_autoderef_mappings (autoderef_mappings_id, - &adjustments); - rust_assert (ok); - - // apply adjustments for the fn call - tree self - = resolve_adjustements (*adjustments, fn_address, expr.get_locus ()); - - // args are always self, and the tuple of the args we are passing where - // self is the path of the call-expr in this case the fn_address - std::vector args; - args.push_back (self); - args.push_back (tuple_args); - - // get the fn call address - tree closure_call_site = ctx->lookup_closure_decl (closure); - tree closure_call_address - = address_expression (closure_call_site, expr.get_locus ()); - translated - = ctx->get_backend ()->call_expression (closure_call_address, args, - nullptr /* static chain ?*/, - expr.get_locus ()); - return; - } + bool possible_trait_call + = generate_possible_fn_trait_call (expr, fn_address, &translated); + if (possible_trait_call) + return; bool is_varadic = false; if (tyty->get_kind () == TyTy::TypeKind::FNDEF) @@ -3073,5 +3030,70 @@ CompileExpr::generate_closure_fntype (HIR::ClosureExpr &expr, return TyTyResolveCompile::compile (ctx, item_tyty); } +bool +CompileExpr::generate_possible_fn_trait_call (HIR::CallExpr &expr, + tree receiver, tree *result) +{ + TyTy::FnType *fn_sig = nullptr; + bool found_overload = ctx->get_tyctx ()->lookup_operator_overload ( + expr.get_mappings ().get_hirid (), &fn_sig); + if (!found_overload) + return false; + + auto id = fn_sig->get_ty_ref (); + auto dId = fn_sig->get_id (); + + tree function = error_mark_node; + bool found_closure = ctx->lookup_function_decl (id, &function, dId, fn_sig); + if (!found_closure) + { + // something went wrong we still return true as this was meant to be an fn + // trait call + *result = error_mark_node; + return true; + } + + // need to apply any autoderef's to the self argument + HirId autoderef_mappings_id = expr.get_mappings ().get_hirid (); + std::vector *adjustments = nullptr; + bool ok = ctx->get_tyctx ()->lookup_autoderef_mappings (autoderef_mappings_id, + &adjustments); + rust_assert (ok); + + // apply adjustments for the fn call + tree self = resolve_adjustements (*adjustments, receiver, expr.get_locus ()); + + // resolve the arguments + std::vector tuple_arg_vals; + for (auto &argument : expr.get_arguments ()) + { + auto rvalue = CompileExpr::Compile (argument.get (), ctx); + tuple_arg_vals.push_back (rvalue); + } + + // this is always the 2nd argument in the function signature + tree fnty = TREE_TYPE (function); + tree fn_arg_tys = TYPE_ARG_TYPES (fnty); + tree tuple_args_tyty_chain = TREE_CHAIN (fn_arg_tys); + tree tuple_args_tyty = TREE_VALUE (tuple_args_tyty_chain); + + tree tuple_args + = ctx->get_backend ()->constructor_expression (tuple_args_tyty, false, + tuple_arg_vals, -1, + expr.get_locus ()); + + // args are always self, and the tuple of the args we are passing where + // self is the path of the call-expr in this case the fn_address + std::vector args; + args.push_back (self); + args.push_back (tuple_args); + + tree call_address = address_expression (function, expr.get_locus ()); + *result = ctx->get_backend ()->call_expression (call_address, args, + nullptr /* static chain ?*/, + expr.get_locus ()); + return true; +} + } // namespace Compile } // namespace Rust diff --git a/gcc/rust/backend/rust-compile-expr.h b/gcc/rust/backend/rust-compile-expr.h index c734406e0da..150a7a4788a 100644 --- a/gcc/rust/backend/rust-compile-expr.h +++ b/gcc/rust/backend/rust-compile-expr.h @@ -152,6 +152,9 @@ protected: tree compiled_closure_tyty, TyTy::FnType **fn_tyty); + bool generate_possible_fn_trait_call (HIR::CallExpr &expr, tree receiver, + tree *result); + private: CompileExpr (Context *ctx); diff --git a/gcc/testsuite/rust/execute/torture/closure2.rs b/gcc/testsuite/rust/execute/torture/closure2.rs new file mode 100644 index 00000000000..45b3b5ce8b4 --- /dev/null +++ b/gcc/testsuite/rust/execute/torture/closure2.rs @@ -0,0 +1,32 @@ +// { dg-output "3\n" } +extern "C" { + fn printf(s: *const i8, ...); +} + +#[lang = "fn_once"] +pub trait FnOnce { + #[lang = "fn_once_output"] + type Output; + + extern "rust-call" fn call_once(self, args: Args) -> Self::Output; +} + +fn f i32>(g: F) { + let call = g(1); + unsafe { + let a = "%i\n\0"; + let b = a as *const str; + let c = b as *const i8; + + printf(c, call); + } +} + +pub fn main() -> i32 { + let a = |i: i32| { + let b = i + 2; + b + }; + f(a); + 0 +}