From patchwork Fri Oct 18 22:27:42 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Martin Sebor X-Patchwork-Id: 1179712 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (sender SPF authorized) smtp.mailfrom=gcc.gnu.org (client-ip=209.132.180.131; helo=sourceware.org; envelope-from=gcc-patches-return-511340-incoming=patchwork.ozlabs.org@gcc.gnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=fail (p=none dis=none) header.from=gmail.com Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=gcc.gnu.org header.i=@gcc.gnu.org header.b="jxzPqz0b"; dkim=fail reason="signature verification failed" (2048-bit key; unprotected) header.d=gmail.com header.i=@gmail.com header.b="NlEfrlcs"; dkim-atps=neutral Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 46w0zK2G6qz9sPK for ; Sat, 19 Oct 2019 09:27:54 +1100 (AEDT) DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender:from :subject:to:message-id:date:mime-version:content-type; q=dns; s= default; b=Tf7y7CdbLal4QuhVUyuRAQh9hGJcx1Ik8axV4HV16Z/FQcQuUIiPf gKOL7XXbLvfB6SUQcZxZtMUR4CguQB/85CqlDdekCuKp2KIhb8c1nQQZfEClYrgZ KNScFAqwDIxVP9UHugBlXW3fqTrZY46BLJrCLCw1gURYiOi2E7hPFU= DKIM-Signature: v=1; a=rsa-sha1; c=relaxed; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender:from :subject:to:message-id:date:mime-version:content-type; s= default; bh=Q8xzwlJt5XnQP7NsHVsgQ9/+ISE=; b=jxzPqz0bXUpqK4Y9gTV+ icpJR1hxo15VLKWKreAPSNXG/xZxhVlEgGAmrqv5xPIGa5f+kLZSkJuYKx+YuDaB +cCIuZq6vemO10Af2sDoe4STtQLpwrL5e70oIyaKV6B42tQr8AOA51rYlsreUKXd 65MjMKq86QgaRuF+jR9wYmo= Received: (qmail 98749 invoked by alias); 18 Oct 2019 22:27:47 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Received: (qmail 98739 invoked by uid 89); 18 Oct 2019 22:27:47 -0000 Authentication-Results: sourceware.org; auth=none X-Spam-SWARE-Status: No, score=-10.7 required=5.0 tests=AWL, BAYES_00, FREEMAIL_FROM, GIT_PATCH_2, GIT_PATCH_3, KAM_ASCII_DIVIDERS, RCVD_IN_DNSWL_NONE, SPF_PASS autolearn=ham version=3.3.1 spammy=corrects, HTo:U*law, HX-HELO:sk:mail-il X-HELO: mail-il1-f177.google.com Received: from mail-il1-f177.google.com (HELO mail-il1-f177.google.com) (209.85.166.177) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with ESMTP; Fri, 18 Oct 2019 22:27:45 +0000 Received: by mail-il1-f177.google.com with SMTP id c12so6960550ilm.1 for ; Fri, 18 Oct 2019 15:27:45 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:subject:to:message-id:date:user-agent:mime-version :content-language; bh=l4dZcAk+Rv9x29jRHaUFdcGhC0zIZbCDWAFwNDFwMq0=; b=NlEfrlcsOw6cFg5HVFGrAXbHx97bJ3Hp8T7b5w/BoX+NrGoMudpmNnlKPeb1WC7jR7 SQ7SVp4SkuvoOFqwfDdLUdAPxDLCxzgPnq/QT9V/WwQC1G+LmTqYTJUlNVnu4a1PlvNF XOW/RKFNGmjIapRdJ1jNTLETCqYPFuPvg1RG1OYMbzpk9tJsNl6a0kzfDC65LJeqItgs xnm99K7bqgnfod4z9m470pVryVgk87yoU9TX+TLj5nPrhOr+J68TkQWGUz3lAXDVwhd2 YXDpJkCZuU81e2HkAv9TJ8Gc9sBkaGnWB+/Nb5rfJLd1TOZuiJRfLVGmEect8UZFLOmK QEKw== Received: from [192.168.0.41] (174-16-107-204.hlrn.qwest.net. [174.16.107.204]) by smtp.gmail.com with ESMTPSA id b8sm2434890ilf.20.2019.10.18.15.27.42 (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Fri, 18 Oct 2019 15:27:43 -0700 (PDT) From: Martin Sebor Subject: [committed] correct strcmp() == 0 result for unknown strings (PR 92157) To: gcc-patches , Jeff Law Message-ID: <1a588e89-1857-c694-114f-65b2ea7b82eb@gmail.com> Date: Fri, 18 Oct 2019 16:27:42 -0600 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:60.0) Gecko/20100101 Thunderbird/60.6.1 MIME-Version: 1.0 X-IsSubscribed: yes The optimization to fold (strcmp() == 0) results involving arrays/strings of unequal size/length has a bug where it is unprepared for the compute_string_length() function to return an invalid length as an indication that the length is unknown. This leads to some strings that are unequal being considered equal. The attached patch corrects this handling. I have committed it in r277194 with Jeff's okay. Martin PR tree-optimization/92157 - incorrect strcmp() == 0 result for unknown strings gcc/testsuite/ChangeLog: PR tree-optimization/92157 * gcc.dg/strlenopt-69.c: Disable test failing due to PR 92155. * gcc.dg/strlenopt-87.c: New test. gcc/ChangeLog: PR tree-optimization/92157 * tree-ssa-strlen.c (handle_builtin_string_cmp): Be prepared for compute_string_length to return a negative result. Index: gcc/testsuite/gcc.dg/strlenopt-69.c =================================================================== --- gcc/testsuite/gcc.dg/strlenopt-69.c (revision 277156) +++ gcc/testsuite/gcc.dg/strlenopt-69.c (working copy) @@ -66,11 +66,14 @@ void test_empty_string (void) b4[2] = '\0'; A (0 == strcmp (&a4[2], &b4[2])); +#if 0 + /* The following isn't handled yet due to PR 92155. */ clobber (a4, b4); memset (a4, 0, sizeof a4); memset (b4, 0, sizeof b4); A (0 == strcmp (a4, b4)); +#endif } /* Verify that comparison of dynamically created strings with unknown Index: gcc/testsuite/gcc.dg/strlenopt-87.c =================================================================== --- gcc/testsuite/gcc.dg/strlenopt-87.c (nonexistent) +++ gcc/testsuite/gcc.dg/strlenopt-87.c (working copy) @@ -0,0 +1,105 @@ +/* PR tree-optimization/92157 - incorrect strcmp() == 0 result for unknown + strings​ + { dg-do run } + { dg-options "-O2 -Wall" } */ + +#include "strlenopt.h" + + +char a2[2], a3[3]; + + +static inline __attribute__ ((always_inline)) int +verify_not_equal (const char *s, const char *t, int x) +{ + int n = x < 0 ? strlen (s) : 0 < x ? strlen (t) : strlen (s) + strlen (t); + + if (strcmp (t, s) == 0) + abort (); + + return n; +} + +__attribute__ ((noipa)) int test_a2_s (const char *s) +{ + return verify_not_equal (a2, s, 0); +} + +__attribute__ ((noipa)) int test_a2_a3 (void) +{ + return verify_not_equal (a2, a3, 0); +} + +__attribute__ ((noipa)) int test_a3_a2 (void) +{ + return verify_not_equal (a3, a2, 0); +} + +__attribute__ ((noipa)) int test_s_a2 (const char *s) +{ + return verify_not_equal (s, a2, 0); +} + + +__attribute__ ((noipa)) int test_a2_s_1 (const char *s) +{ + return verify_not_equal (a2, s, -1); +} + +__attribute__ ((noipa)) int test_a2_a3_1 (void) +{ + return verify_not_equal (a2, a3, -1); +} + +__attribute__ ((noipa)) int test_a3_a2_1 (void) +{ + return verify_not_equal (a3, a2, -1); +} + +__attribute__ ((noipa)) int test_s_a2_1 (const char *s) +{ + return verify_not_equal (s, a2, -1); +} + + +__attribute__ ((noipa)) int test_a2_s_2 (const char *s) +{ + return verify_not_equal (a2, s, +1); +} + +__attribute__ ((noipa)) int test_a2_a3_2 (void) +{ + return verify_not_equal (a2, a3, +1); +} + +__attribute__ ((noipa)) int test_a3_a2_2 (void) +{ + return verify_not_equal (a3, a2, +1); +} + +__attribute__ ((noipa)) int test_s_a2_2 (const char *s) +{ + return verify_not_equal (s, a2, +1); +} + +int main (void) +{ + a2[0] = '1'; + a3[0] = '1'; + a3[0] = '2'; + + test_a2_s (""); + test_a2_a3 (); + test_a3_a2 (); + test_s_a2 (""); + + test_a2_s_1 (""); + test_a2_a3_1 (); + test_a3_a2_1 (); + test_s_a2_1 (""); + + test_a2_s_2 (""); + test_a2_a3_2 (); + test_a3_a2_2 (); + test_s_a2_2 (""); +} Index: gcc/tree-ssa-strlen.c =================================================================== --- gcc/tree-ssa-strlen.c (revision 277156) +++ gcc/tree-ssa-strlen.c (working copy) @@ -3842,7 +3842,7 @@ handle_builtin_string_cmp (gimple_stmt_iterator *g HOST_WIDE_INT arysiz1 = -1, arysiz2 = -1; if (idx1) - cstlen1 = compute_string_length (idx1) + 1; + cstlen1 = compute_string_length (idx1); else arysiz1 = determine_min_objsize (arg1); @@ -3853,7 +3853,7 @@ handle_builtin_string_cmp (gimple_stmt_iterator *g /* Repeat for the second argument. */ if (idx2) - cstlen2 = compute_string_length (idx2) + 1; + cstlen2 = compute_string_length (idx2); else arysiz2 = determine_min_objsize (arg2); @@ -3860,6 +3860,14 @@ handle_builtin_string_cmp (gimple_stmt_iterator *g if (cstlen2 < 0 && arysiz2 < 0) return false; + if (cstlen1 < 0 && cstlen2 < 0) + return false; + + if (cstlen1 >= 0) + ++cstlen1; + if (cstlen2 >= 0) + ++cstlen2; + /* The exact number of characters to compare. */ HOST_WIDE_INT cmpsiz = bound < 0 ? cstlen1 < 0 ? cstlen2 : cstlen1 : bound; /* The size of the array in which the unknown string is stored. */