From patchwork Sat May 25 18:42:00 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jeff Law X-Patchwork-Id: 1939281 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@legolas.ozlabs.org Authentication-Results: legolas.ozlabs.org; dkim=pass (2048-bit key; unprotected) header.d=ventanamicro.com header.i=@ventanamicro.com header.a=rsa-sha256 header.s=google header.b=n2xTrtkq; dkim-atps=neutral Authentication-Results: legolas.ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=2620:52:3:1:0:246e:9693:128c; helo=server2.sourceware.org; envelope-from=gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org; receiver=patchwork.ozlabs.org) Received: from server2.sourceware.org (server2.sourceware.org [IPv6:2620:52:3:1:0:246e:9693:128c]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits) key-exchange X25519 server-signature ECDSA (secp384r1) server-digest SHA384) (No client certificate requested) by legolas.ozlabs.org (Postfix) with ESMTPS id 4VmrPS2Q73z20KL for ; Sun, 26 May 2024 04:42:34 +1000 (AEST) Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id CDE6A385E45C for ; Sat, 25 May 2024 18:42:26 +0000 (GMT) X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from mail-pj1-x1034.google.com (mail-pj1-x1034.google.com [IPv6:2607:f8b0:4864:20::1034]) by sourceware.org (Postfix) with ESMTPS id E43343858CD9 for ; Sat, 25 May 2024 18:42:04 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org E43343858CD9 Authentication-Results: sourceware.org; dmarc=none (p=none dis=none) header.from=ventanamicro.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=ventanamicro.com ARC-Filter: OpenARC Filter v1.0.0 sourceware.org E43343858CD9 Authentication-Results: server2.sourceware.org; arc=none smtp.remote-ip=2607:f8b0:4864:20::1034 ARC-Seal: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1716662527; cv=none; b=w8ZX3U0gcU6CaowWD8AUjEf8fbCvSsa/VuWSeO1kkWvdTKfmAqbGWz22JOQ2ynKS+g6end7ZqPcnlk87bEw5NmmDsYq+8LCwKBqlmkCa2uZlTrZffGQ1/aYZAlHqHBwAFoj2ioir3rPwpGrJhlJh7BtZyPYGqQ/1UMAG58H/DLE= ARC-Message-Signature: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1716662527; c=relaxed/simple; bh=JjUa/reDamY5Z+yygdQ5xt4HReokWsuvZzPC0KgNl3I=; h=DKIM-Signature:Message-ID:Date:MIME-Version:From:To:Subject; b=ai5RcDldDvK2EXh7RwpGhjO0VQp5KYmkv3ZhFHD00JeL5fPFyeKlG+zd2a8lW3lnjujeplWRFWbv3sO6S4PxQnPMSzu7Qp6nzWLKQqfCy6xJtuOuoYp3RsMP9PCM9Iw2+ZJtrXL3Z4trRxv+piUf9+2gw1kp6HDvy9WeJZhRXx0= ARC-Authentication-Results: i=1; server2.sourceware.org Received: by mail-pj1-x1034.google.com with SMTP id 98e67ed59e1d1-2bf629ff55bso1450152a91.1 for ; Sat, 25 May 2024 11:42:04 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=ventanamicro.com; s=google; t=1716662523; x=1717267323; darn=gcc.gnu.org; h=subject:to:from:content-language:user-agent:mime-version:date :message-id:from:to:cc:subject:date:message-id:reply-to; bh=Z3Rc0crE/WlNj5FNYfDtP2/N+lC7SVw4w7tFzwg4458=; b=n2xTrtkqdpIrT3n8cqiDTUOiSWRz9Qm9EDUZjBv1TtN/M668n82emIHnzwZvz4Q8co E2OJrZUDDOYScE7yAYO2mAzbsSL7rc8fVXLCUJW9Bj/hj4BLsycmpuBoBJiYak9fugMF x1iie4aSqhxA7gZB6wUKg/OSK904pC2gWT8KAEJkZ3EpYNaejQxyoCqSzkO5Qd4CcojR jE2klqZi8zLN9yX+Gf3Y4TyVXx5knz40Xw44Fx18UXWyDMcQKw4fxNmkuZJXsV6l8ZTL ugLp116ytqLxa4vZRto6tpYMgKpmSl+3mBjBO/NstUrSJAMWP4lm3B711hkGxvR4iah/ wZig== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1716662523; x=1717267323; h=subject:to:from:content-language:user-agent:mime-version:date :message-id:x-gm-message-state:from:to:cc:subject:date:message-id :reply-to; bh=Z3Rc0crE/WlNj5FNYfDtP2/N+lC7SVw4w7tFzwg4458=; b=P9Q1Id4BSUENug/ZLgRMappyz7xRlVcFoWk39RPQMGTtDGifNrZkgiIlneew5+S9Iq W/93fzJrVFB42SNI0wc7qLepsnas8qDEjntJavzn9MjskMjz1pTBXAJnehKXU+1PvrKg m5OR6EXN/T7q+uJdsm5wUrGL0wBb3UeS8GudGeq7otu/uxePOPt6Xj1rCnjCoMZL0TSq Y2sKZIpH/Sz1TvzEE4MHN//w40XhbSg84eoopzWzfN5BtZf674wusjbNg9KHD9RLQ5MI 6NqpA4xDJnprukUx7I3XAIhPy0ymbHMxzMm27M7kZA7EW1P7+dYpD8b6r0gJw8hlzVjL tlMg== X-Gm-Message-State: AOJu0YxjSbkEDlPZCA1HGd0k5MZAnLUI9icQwUR44i9/3y+TYsXf/TXx F+H4qAU9/y4Aj117ocIJLnxvSWJydY0Azb8itbUsu/itkIDnSSnLEAlogslBjp19O95SN/Wmbd9 G X-Google-Smtp-Source: AGHT+IFcZAdbK+MRl9bDsW1zV9+aUC5uZ4CQcgwq4xmXleuyN47MyHjot5viaAdmcgDMMbHlDccFFg== X-Received: by 2002:a17:90a:e295:b0:2bf:1962:ea08 with SMTP id 98e67ed59e1d1-2bf5f74d855mr4343360a91.45.1716662522861; Sat, 25 May 2024 11:42:02 -0700 (PDT) Received: from [172.31.0.109] ([136.36.72.243]) by smtp.gmail.com with ESMTPSA id 98e67ed59e1d1-2bf7dde2486sm1870514a91.54.2024.05.25.11.42.01 for (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Sat, 25 May 2024 11:42:01 -0700 (PDT) Message-ID: Date: Sat, 25 May 2024 12:42:00 -0600 MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Beta Content-Language: en-US From: Jeff Law To: "gcc-patches@gcc.gnu.org" Subject: [committed] [v2] More logical op simplifications in simplify-rtx.cc X-Spam-Status: No, score=-11.0 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=ham 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.30 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: gcc-patches-bounces+incoming=patchwork.ozlabs.org@gcc.gnu.org This is a revamp of what started as a target specific patch. Basically xalan (corrected, I originally thought it was perlbench) has a bitset implementation with a bit of an oddity. Specifically setBit will clear the bit before it is set: > if (bitToSet < 32) > { > fBits1 &= ~mask; > fBits1 |= mask; > } > else > { > fBits2 &= ~mask; > fBits2 |= mask; > } We can clean this up pretty easily in RTL with a small bit of code in simplify-rtx. While xalan doesn't have other cases, we can synthesize tests pretty easily and handle them as well. It turns out we don't actually have to recognize this stuff at the bit level, just standard logical identities are sufficient. For example (X | Y) & ~Y -> X & ~Y Andrew P. might poke at this at the gimple level. The type changes kindof get in the way in gimple but he's much better at match.pd than I am, so if he wants to chase it from the gimple side, I'll fully support that. Bootstrapped and regression tested on x86. Also run through my tester on its embedded targets. Pushing to the trunk. jeff commit 05daf617ea22e1d818295ed2d037456937e23530 Author: Jeff Law Date: Sat May 25 12:39:05 2024 -0600 [committed] [v2] More logical op simplifications in simplify-rtx.cc This is a revamp of what started as a target specific patch. Basically xalan (corrected, I originally thought it was perlbench) has a bitset implementation with a bit of an oddity. Specifically setBit will clear the bit before it is set: > if (bitToSet < 32) > { > fBits1 &= ~mask; > fBits1 |= mask; > } > else > { > fBits2 &= ~mask; > fBits2 |= mask; > } We can clean this up pretty easily in RTL with a small bit of code in simplify-rtx. While xalan doesn't have other cases, we can synthesize tests pretty easily and handle them as well. It turns out we don't actually have to recognize this stuff at the bit level, just standard logical identities are sufficient. For example (X | Y) & ~Y -> X & ~Y Andrew P. might poke at this at the gimple level. The type changes kindof get in the way in gimple but he's much better at match.pd than I am, so if he wants to chase it from the gimple side, I'll fully support that. Bootstrapped and regression tested on x86. Also run through my tester on its embedded targets. Pushing to the trunk. gcc/ * simplify-rtx.cc (simplify_context::simplify_binary_operation_1): Handle more logical simplifications. gcc/testsuite/ * g++.target/riscv/redundant-bitmap-1.C: New test. * g++.target/riscv/redundant-bitmap-2.C: New test. * g++.target/riscv/redundant-bitmap-3.C: New test. * g++.target/riscv/redundant-bitmap-4.C: New test. diff --git a/gcc/simplify-rtx.cc b/gcc/simplify-rtx.cc index 53f54d1d392..5caf1dfd957 100644 --- a/gcc/simplify-rtx.cc +++ b/gcc/simplify-rtx.cc @@ -3549,6 +3549,12 @@ simplify_context::simplify_binary_operation_1 (rtx_code code, return tem; } + /* Convert (ior (and (not A) B) A) into A | B. */ + if (GET_CODE (op0) == AND + && GET_CODE (XEXP (op0, 0)) == NOT + && rtx_equal_p (XEXP (XEXP (op0, 0), 0), op1)) + return simplify_gen_binary (IOR, mode, XEXP (op0, 1), op1); + tem = simplify_byte_swapping_operation (code, mode, op0, op1); if (tem) return tem; @@ -3801,6 +3807,12 @@ simplify_context::simplify_binary_operation_1 (rtx_code code, return tem; } + /* Convert (xor (and (not A) B) A) into A | B. */ + if (GET_CODE (op0) == AND + && GET_CODE (XEXP (op0, 0)) == NOT + && rtx_equal_p (XEXP (XEXP (op0, 0), 0), op1)) + return simplify_gen_binary (IOR, mode, XEXP (op0, 1), op1); + tem = simplify_byte_swapping_operation (code, mode, op0, op1); if (tem) return tem; @@ -4006,6 +4018,23 @@ simplify_context::simplify_binary_operation_1 (rtx_code code, && rtx_equal_p (op1, XEXP (XEXP (op0, 1), 0))) return simplify_gen_binary (AND, mode, op1, XEXP (op0, 0)); + /* (and (ior/xor (X Y) (not Y)) -> X & ~Y */ + if ((GET_CODE (op0) == IOR || GET_CODE (op0) == XOR) + && GET_CODE (op1) == NOT + && rtx_equal_p (XEXP (op1, 0), XEXP (op0, 1))) + return simplify_gen_binary (AND, mode, XEXP (op0, 0), + simplify_gen_unary (NOT, mode, + XEXP (op1, 0), + mode)); + /* (and (ior/xor (Y X) (not Y)) -> X & ~Y */ + if ((GET_CODE (op0) == IOR || GET_CODE (op0) == XOR) + && GET_CODE (op1) == NOT + && rtx_equal_p (XEXP (op1, 0), XEXP (op0, 0))) + return simplify_gen_binary (AND, mode, XEXP (op0, 1), + simplify_gen_unary (NOT, mode, + XEXP (op1, 0), + mode)); + /* Convert (and (ior A C) (ior B C)) into (ior (and A B) C). */ if (GET_CODE (op0) == GET_CODE (op1) && (GET_CODE (op0) == AND diff --git a/gcc/testsuite/g++.target/riscv/redundant-bitmap-1.C b/gcc/testsuite/g++.target/riscv/redundant-bitmap-1.C new file mode 100644 index 00000000000..37066f10eea --- /dev/null +++ b/gcc/testsuite/g++.target/riscv/redundant-bitmap-1.C @@ -0,0 +1,14 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -march=rv64gc_zba_zbb_zbs -mabi=lp64" } */ + +void setBit(char &a, int b) { + char c = 0x1UL << b; + a &= ~c; + a |= c; +} + +/* { dg-final { scan-assembler-not "bclr\t" } } */ +/* { dg-final { scan-assembler-not "andn\t" } } */ +/* { dg-final { scan-assembler-not "or\t" } } */ +/* { dg-final { scan-assembler-times "bset\t" 1 } } */ + diff --git a/gcc/testsuite/g++.target/riscv/redundant-bitmap-2.C b/gcc/testsuite/g++.target/riscv/redundant-bitmap-2.C new file mode 100644 index 00000000000..86acaba298f --- /dev/null +++ b/gcc/testsuite/g++.target/riscv/redundant-bitmap-2.C @@ -0,0 +1,14 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -march=rv64gc_zba_zbb_zbs -mabi=lp64" } */ + +void setBit(char &a, int b) { + char c = 0x1UL << b; + a &= ~c; + a ^= c; +} + +/* { dg-final { scan-assembler-not "bclr\t" } } */ +/* { dg-final { scan-assembler-not "xor\t" } } */ +/* { dg-final { scan-assembler-not "andn\t" } } */ +/* { dg-final { scan-assembler-times "bset\t" 1 } } */ + diff --git a/gcc/testsuite/g++.target/riscv/redundant-bitmap-3.C b/gcc/testsuite/g++.target/riscv/redundant-bitmap-3.C new file mode 100644 index 00000000000..16bd7c1785e --- /dev/null +++ b/gcc/testsuite/g++.target/riscv/redundant-bitmap-3.C @@ -0,0 +1,14 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -march=rv64gc_zba_zbb_zbs -mabi=lp64" } */ + +void setBit(char &a, int b) { + char c = 0x1UL << b; + a |= c; + a &= ~c; +} + +/* { dg-final { scan-assembler-not "bset\t" } } */ +/* { dg-final { scan-assembler-not "or\t" } } */ +/* { dg-final { scan-assembler-not "andn\t" } } */ +/* { dg-final { scan-assembler-times "bclr\t" 1 } } */ + diff --git a/gcc/testsuite/g++.target/riscv/redundant-bitmap-4.C b/gcc/testsuite/g++.target/riscv/redundant-bitmap-4.C new file mode 100644 index 00000000000..f664ee01a01 --- /dev/null +++ b/gcc/testsuite/g++.target/riscv/redundant-bitmap-4.C @@ -0,0 +1,14 @@ +/* { dg-do compile } */ +/* { dg-options "-O2 -march=rv64gc_zba_zbb_zbs -mabi=lp64" } */ + +void setBit(char &a, int b) { + char c = 0x1UL << b; + a ^= c; + a &= ~c; +} + +/* { dg-final { scan-assembler-not "binv\t" } } */ +/* { dg-final { scan-assembler-not "xor\t" } } */ +/* { dg-final { scan-assembler-not "andn\t" } } */ +/* { dg-final { scan-assembler-times "bclr\t" 1 } } */ +