From patchwork Thu Feb 11 09:49:08 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jakub Jelinek X-Patchwork-Id: 581788 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org 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 D69C614090B for ; Thu, 11 Feb 2016 20:49:28 +1100 (AEDT) Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=gcc.gnu.org header.i=@gcc.gnu.org header.b=hjI2awA/; dkim-atps=neutral DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender:date :from:to:subject:message-id:reply-to:mime-version:content-type; q=dns; s=default; b=kvluRsH8j/GhCIznyZ09kotCbWaeNZWoWDovQZJrdvH xb7jmWyJO4wPx4l02lfVh7F8I7zqVEO9thJNlR99XAvWoFP93cWPz4ivBD/gZoQ2 Bi4V0PiySd5zNfSjWvoq0SsbULVO8oVSy7wWOfjkogPpjxJJ/nhVSYAHhUm5UALM = 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:date :from:to:subject:message-id:reply-to:mime-version:content-type; s=default; bh=mnOYPJW1Sl0Zxh3k/6pCXS/WFGY=; b=hjI2awA/0HEqQ3v9E uePu2Q6mhZkjhNSvaY5gQe1MXpp1x/F51t8Kg8j3JWk9UwnCicpoojHEJrUTd8Zi 2nDMJ67rtX599lyASV34imUeDbWy08Y7IVFm/qw2CUwP0FZ7d+gr2tvy8B9peWgN qIV6BVWu0/t3WlLrgyqR+Ue09k= Received: (qmail 54308 invoked by alias); 11 Feb 2016 09:49:20 -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 54289 invoked by uid 89); 11 Feb 2016 09:49:19 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=-2.1 required=5.0 tests=BAYES_00, RP_MATCHES_RCVD, SPF_HELO_PASS autolearn=ham version=3.3.2 spammy=shrink-wrapping, shrinkwrapping, 2987, 5219 X-HELO: mx1.redhat.com Received: from mx1.redhat.com (HELO mx1.redhat.com) (209.132.183.28) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with (AES256-GCM-SHA384 encrypted) ESMTPS; Thu, 11 Feb 2016 09:49:14 +0000 Received: from int-mx13.intmail.prod.int.phx2.redhat.com (int-mx13.intmail.prod.int.phx2.redhat.com [10.5.11.26]) by mx1.redhat.com (Postfix) with ESMTPS id 98CBCC0A805A for ; Thu, 11 Feb 2016 09:49:13 +0000 (UTC) Received: from tucnak.zalov.cz ([10.3.113.11]) by int-mx13.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id u1B9nBqu004823 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-GCM-SHA384 bits=256 verify=NO) for ; Thu, 11 Feb 2016 04:49:12 -0500 Received: from tucnak.zalov.cz (localhost [127.0.0.1]) by tucnak.zalov.cz (8.15.2/8.15.2) with ESMTP id u1B9n939028590 for ; Thu, 11 Feb 2016 10:49:10 +0100 Received: (from jakub@localhost) by tucnak.zalov.cz (8.15.2/8.15.2/Submit) id u1B9n8uo028589 for gcc-patches@gcc.gnu.org; Thu, 11 Feb 2016 10:49:08 +0100 Date: Thu, 11 Feb 2016 10:49:08 +0100 From: Jakub Jelinek To: gcc-patches@gcc.gnu.org Subject: gcc-4_9-branch backports Message-ID: <20160211094908.GA3017@tucnak.redhat.com> Reply-To: Jakub Jelinek MIME-Version: 1.0 Content-Disposition: inline User-Agent: Mutt/1.5.24 (2015-08-30) X-IsSubscribed: yes Hi! I've committed following backports of my trunk commits to gcc-4_9-branch after bootstrapping/regtesting them on x86_64-linux and i686-linux. Jakub 2016-02-11 Jakub Jelinek Backported from mainline 2015-11-19 Jakub Jelinek PR preprocessor/60736 * include/cpplib.h (cpp_errno_filename): New prototype. * errors.c (cpp_errno): Don't handle msgid "" specially, use _(msgid) instead of msgid as argument to cpp_error. (cpp_errno_filename): New function. * files.c (read_file_guts): Use cpp_errno_filename instead of cpp_errno. (open_file_failed): Likewise. Use file->name if file->path is NULL in diagnostics. 2016-02-11 Jakub Jelinek Backported from mainline 2015-11-19 Jakub Jelinek PR target/67770 * config/i386/i386.md (simple_return): Disable if ix86_static_chain_on_stack is true. * gcc.target/i386/pr67770.c: New test. --- gcc/config/i386/i386.md (revision 230592) +++ gcc/config/i386/i386.md (revision 230593) @@ -12203,10 +12203,14 @@ (define_expand "return" ;; We need to disable this for TARGET_SEH, as otherwise ;; shrink-wrapped prologue gets enabled too. This might exceed ;; the maximum size of prologue in unwind information. +;; Also disallow shrink-wrapping if using stack slot to pass the +;; static chain pointer - the first instruction has to be pushl %esi +;; and it can't be moved around, as we use alternate entry points +;; in that case. (define_expand "simple_return" [(simple_return)] - "!TARGET_SEH" + "!TARGET_SEH && !ix86_static_chain_on_stack" { if (crtl->args.pops_args) { --- gcc/testsuite/gcc.target/i386/pr67770.c (revision 0) +++ gcc/testsuite/gcc.target/i386/pr67770.c (revision 230593) @@ -0,0 +1,40 @@ +/* PR target/67770 */ +/* { dg-do run { target ia32 } } */ +/* { dg-require-effective-target trampolines } */ +/* { dg-options "-O2" } */ + +#ifndef NO_TRAMPOLINES +__attribute__ ((noinline)) void +foo (int i, void (* __attribute__ ((regparm (3))) bar) (int)) +{ + bar (i); +} +#endif + +int +main () +{ +#ifndef NO_TRAMPOLINES + int p = 0; + + __attribute__ ((regparm (3), noinline)) void + bar (int i) + { + if (__builtin_expect (i, 0)) + ++p; + } + + foo (0, bar); + bar (0); + + if (p != 0) + __builtin_abort (); + + foo (1, bar); + bar (1); + + if (p != 2) + __builtin_abort (); +#endif + return 0; +} 2016-02-11 Jakub Jelinek Backported from mainline 2015-11-21 Jakub Jelinek PR debug/66432 * tree-inline.c (copy_debug_stmt): If gimple_debug_source_bind_get_value is DECL_ORIGIN of a PARM_DECL in decl_debug_args, don't call remap_gimple_op_r on it. * gcc.dg/debug/pr66432.c: New test. --- gcc/tree-inline.c (revision 230701) +++ gcc/tree-inline.c (revision 230702) @@ -2864,8 +2864,6 @@ copy_debug_stmt (gdebug *stmt, copy_body else if (gimple_debug_source_bind_p (stmt)) { gimple_debug_source_bind_set_var (stmt, t); - walk_tree (gimple_debug_source_bind_get_value_ptr (stmt), - remap_gimple_op_r, &wi, NULL); /* When inlining and source bind refers to one of the optimized away parameters, change the source bind into normal debug bind referring to the corresponding DEBUG_EXPR_DECL that should have @@ -2889,7 +2887,10 @@ copy_debug_stmt (gdebug *stmt, copy_body break; } } - } + } + if (gimple_debug_source_bind_p (stmt)) + walk_tree (gimple_debug_source_bind_get_value_ptr (stmt), + remap_gimple_op_r, &wi, NULL); } processing_debug_stmt = 0; --- gcc/testsuite/gcc.dg/debug/pr66432.c (revision 0) +++ gcc/testsuite/gcc.dg/debug/pr66432.c (revision 230702) @@ -0,0 +1,19 @@ +/* PR debug/66432 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -g" } */ + +extern void baz (const char *, const char *) __attribute__ ((__noreturn__)); + +void +foo (int x, int y[x][x]) +{ + if (x < 2) + baz ("", ""); +} + +void +bar (void) +{ + int z[2][2] = { { 1, 2 }, { 3, 4 } }; + foo (2, z); +} 2016-02-11 Jakub Jelinek Backported from mainline 2015-12-03 Jakub Jelinek PR preprocessor/57580 * c-ppoutput.c (print): Change printed field to bool. (init_pp_output): Set print.printed to false instead of 0. (scan_translation_unit): Fix up formatting. Set print.printed to true after printing something other than newline. (scan_translation_unit_trad): Set print.printed to true instead of 1. (maybe_print_line_1): Set print.printed to false instead of 0. (print_line_1): Likewise. (do_line_change): Set print.printed to true instead of 1. (cb_define, dump_queued_macros, cb_include, cb_def_pragma, dump_macro): Set print.printed to false after printing newline. * c-c++-common/cpp/pr57580.c: New test. * c-c++-common/gomp/pr57580.c: New test. --- gcc/c-family/c-ppoutput.c (revision 231212) +++ gcc/c-family/c-ppoutput.c (revision 231213) @@ -33,7 +33,7 @@ static struct const cpp_token *prev; /* Previous token. */ const cpp_token *source; /* Source token for spacing. */ int src_line; /* Line number currently being written. */ - unsigned char printed; /* Nonzero if something output at line. */ + bool printed; /* True if something output at line. */ bool first_time; /* pp_file_change hasn't been called yet. */ const char *src_file; /* Current source file. */ } print; @@ -151,7 +151,7 @@ init_pp_output (FILE *out_stream) /* Initialize the print structure. */ print.src_line = 1; - print.printed = 0; + print.printed = false; print.prev = 0; print.outf = out_stream; print.first_time = 1; @@ -202,12 +202,16 @@ scan_translation_unit (cpp_reader *pfile { do_line_change (pfile, token, loc, false); putc (' ', print.outf); + print.printed = true; } else if (print.source->flags & PREV_WHITE || (print.prev && cpp_avoid_paste (pfile, print.prev, token)) || (print.prev == NULL && token->type == CPP_HASH)) - putc (' ', print.outf); + { + putc (' ', print.outf); + print.printed = true; + } } else if (token->flags & PREV_WHITE) { @@ -218,6 +222,7 @@ scan_translation_unit (cpp_reader *pfile && !in_pragma) do_line_change (pfile, token, loc, false); putc (' ', print.outf); + print.printed = true; } avoid_paste = false; @@ -235,7 +240,7 @@ scan_translation_unit (cpp_reader *pfile fprintf (print.outf, "%s %s", space, name); else fprintf (print.outf, "%s", name); - print.printed = 1; + print.printed = true; in_pragma = true; } else if (token->type == CPP_PRAGMA_EOL) @@ -246,9 +251,9 @@ scan_translation_unit (cpp_reader *pfile else { if (cpp_get_options (parse_in)->debug) - linemap_dump_location (line_table, token->src_loc, - print.outf); + linemap_dump_location (line_table, token->src_loc, print.outf); cpp_output_token (token, print.outf); + print.printed = true; } /* CPP_COMMENT tokens and raw-string literal tokens can @@ -298,7 +303,7 @@ scan_translation_unit_trad (cpp_reader * size_t len = pfile->out.cur - pfile->out.base; maybe_print_line (pfile->out.first_line); fwrite (pfile->out.base, 1, len, print.outf); - print.printed = 1; + print.printed = true; if (!CPP_OPTION (pfile, discard_comments)) account_for_newlines (pfile->out.base, len); } @@ -319,7 +324,7 @@ maybe_print_line_1 (source_location src_ { putc ('\n', stream); print.src_line++; - print.printed = 0; + print.printed = false; } if (!flag_no_line_commands @@ -360,7 +365,7 @@ print_line_1 (source_location src_loc, c /* End any previous line of text. */ if (print.printed) putc ('\n', stream); - print.printed = 0; + print.printed = false; if (!flag_no_line_commands) { @@ -429,7 +434,7 @@ do_line_change (cpp_reader *pfile, const if (!CPP_OPTION (pfile, traditional)) { int spaces = LOCATION_COLUMN (src_loc) - 2; - print.printed = 1; + print.printed = true; while (-- spaces >= 0) putc (' ', print.outf); @@ -470,6 +475,7 @@ cb_define (cpp_reader *pfile, source_loc fputs ((const char *) NODE_NAME (node), print.outf); putc ('\n', print.outf); + print.printed = false; linemap_resolve_location (line_table, line, LRK_MACRO_DEFINITION_LOCATION, &map); @@ -521,7 +527,7 @@ dump_queued_macros (cpp_reader *pfile AT { putc ('\n', print.outf); print.src_line++; - print.printed = 0; + print.printed = false; } for (q = define_queue; q;) @@ -530,6 +536,7 @@ dump_queued_macros (cpp_reader *pfile AT fputs ("#define ", print.outf); fputs (q->macro, print.outf); putc ('\n', print.outf); + print.printed = false; print.src_line++; oq = q; q = q->next; @@ -573,6 +580,7 @@ cb_include (cpp_reader *pfile ATTRIBUTE_ } putc ('\n', print.outf); + print.printed = false; print.src_line++; } @@ -638,6 +646,7 @@ cb_def_pragma (cpp_reader *pfile, source maybe_print_line (line); fputs ("#pragma ", print.outf); cpp_output_line (pfile, print.outf); + print.printed = false; print.src_line++; } @@ -651,6 +660,7 @@ dump_macro (cpp_reader *pfile, cpp_hashn fputs ((const char *) cpp_macro_definition (pfile, node), print.outf); putc ('\n', print.outf); + print.printed = false; print.src_line++; } --- gcc/testsuite/c-c++-common/cpp/pr57580.c (revision 0) +++ gcc/testsuite/c-c++-common/cpp/pr57580.c (revision 231213) @@ -0,0 +1,9 @@ +/* PR preprocessor/57580 */ +/* { dg-do compile } */ +/* { dg-options "-save-temps" } */ + +#define MSG \ + _Pragma("message(\"message0\")") \ + _Pragma("message(\"message1\")") +MSG /* { dg-message "message0" } */ +/* { dg-message "message1" "" { target *-*-* } 8 } */ --- gcc/testsuite/c-c++-common/gomp/pr57580.c (revision 0) +++ gcc/testsuite/c-c++-common/gomp/pr57580.c (revision 231213) @@ -0,0 +1,36 @@ +/* PR preprocessor/57580 */ +/* { dg-do compile } */ +/* { dg-options "-fopenmp -save-temps -fdump-tree-gimple" } */ + +#define PS \ + _Pragma("omp parallel num_threads(2)") \ + { \ + _Pragma("omp single") \ + { \ + ret = 0; \ + } \ + } + +int +main () +{ + int ret; + _Pragma("omp parallel num_threads(3)") + { + _Pragma("omp single") + { + ret = 0; + } + } + _Pragma("omp parallel num_threads(4)") { _Pragma("omp single") { ret = 0; } } + { _Pragma("omp parallel num_threads(5)") { _Pragma("omp single") { ret = 0; } } } + PS + PS + return ret; +} + +/* { dg-final { scan-tree-dump-times "#pragma omp parallel\[^\n\r]*num_threads\\(2\\)" 2 "gimple" } } */ +/* { dg-final { scan-tree-dump-times "#pragma omp parallel\[^\n\r]*num_threads\\(3\\)" 1 "gimple" } } */ +/* { dg-final { scan-tree-dump-times "#pragma omp parallel\[^\n\r]*num_threads\\(4\\)" 1 "gimple" } } */ +/* { dg-final { scan-tree-dump-times "#pragma omp parallel\[^\n\r]*num_threads\\(5\\)" 1 "gimple" } } */ +/* { dg-final { scan-tree-dump-times "#pragma omp single" 5 "gimple" } } */ 2016-02-11 Jakub Jelinek Backported from mainline 2015-12-04 Jakub Jelinek PR tree-optimization/68680 * calls.c (special_function_p): Return ECF_MAY_BE_ALLOCA for BUILT_IN_ALLOCA{,_WITH_ALIGN}. Don't check for __builtin_alloca by name. * gcc.target/i386/pr68680.c: New test. --- gcc/calls.c (revision 231278) +++ gcc/calls.c (revision 231279) @@ -521,12 +521,9 @@ special_function_p (const_tree fndecl, i /* We assume that alloca will always be called by name. It makes no sense to pass it as a pointer-to-function to anything that does not understand its behavior. */ - if (((IDENTIFIER_LENGTH (DECL_NAME (fndecl)) == 6 - && name[0] == 'a' - && ! strcmp (name, "alloca")) - || (IDENTIFIER_LENGTH (DECL_NAME (fndecl)) == 16 - && name[0] == '_' - && ! strcmp (name, "__builtin_alloca")))) + if (IDENTIFIER_LENGTH (DECL_NAME (fndecl)) == 6 + && name[0] == 'a' + && ! strcmp (name, "alloca")) flags |= ECF_MAY_BE_ALLOCA; /* Disregard prefix _, __, __x or __builtin_. */ @@ -572,6 +569,17 @@ special_function_p (const_tree fndecl, i flags |= ECF_NORETURN; } + if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_NORMAL) + switch (DECL_FUNCTION_CODE (fndecl)) + { + case BUILT_IN_ALLOCA: + case BUILT_IN_ALLOCA_WITH_ALIGN: + flags |= ECF_MAY_BE_ALLOCA; + break; + default: + break; + } + return flags; } --- gcc/testsuite/gcc.target/i386/pr68680.c (revision 0) +++ gcc/testsuite/gcc.target/i386/pr68680.c (revision 231279) @@ -0,0 +1,15 @@ +/* PR tree-optimization/68680 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -fstack-protector-strong" } */ + +int foo (char *); + +int +bar (unsigned long x) +{ + char a[x]; + return foo (a); +} + +/* Verify that this function is stack protected. */ +/* { dg-final { scan-assembler "stack_chk_fail" } } */ 2016-02-11 Jakub Jelinek Backported from mainline 2015-12-10 Jakub Jelinek PR rtl-optimization/68376 PR rtl-optimization/68670 * ifcvt.c (noce_try_abs): For one_cmpl allow < 0, >= 0 or > -1 conditions regardless of negate, and disallow all other conditions. * gcc.c-torture/execute/pr68376-2.c (f5, f6, f7, f8): New tests. (main): Call them. * gcc.dg/pr68670-1.c: New test. * gcc.dg/pr68670-2.c: New test. 2015-11-19 Jakub Jelinek PR rtl-optimization/68376 * ifcvt.c (noce_try_abs): Disable one_cmpl optimization if encountering x <= 0 ? ~x : x or x > 0 ? ~x : x. * gcc.c-torture/execute/pr68376-1.c: New test. * gcc.c-torture/execute/pr68376-2.c: New test. --- gcc/ifcvt.c (revision 230595) +++ gcc/ifcvt.c (revision 231526) @@ -2071,12 +2071,26 @@ noce_try_abs (struct noce_if_info *if_in /* Work around funny ideas get_condition has wrt canonicalization. Note that these rtx constants are known to be CONST_INT, and - therefore imply integer comparisons. */ + therefore imply integer comparisons. + The one_cmpl case is more complicated, as we want to handle + only x < 0 ? ~x : x or x >= 0 ? x : ~x to one_cmpl_abs (x) + and x < 0 ? x : ~x or x >= 0 ? ~x : x to ~one_cmpl_abs (x), + but not other cases (x > -1 is equivalent of x >= 0). */ if (c == constm1_rtx && GET_CODE (cond) == GT) ; else if (c == const1_rtx && GET_CODE (cond) == LT) - ; - else if (c != CONST0_RTX (GET_MODE (b))) + { + if (one_cmpl) + return FALSE; + } + else if (c == CONST0_RTX (GET_MODE (b))) + { + if (one_cmpl + && GET_CODE (cond) != GE + && GET_CODE (cond) != LT) + return FALSE; + } + else return FALSE; /* Determine what sort of operation this is. */ --- gcc/testsuite/gcc.c-torture/execute/pr68376-1.c (revision 0) +++ gcc/testsuite/gcc.c-torture/execute/pr68376-1.c (revision 230596) @@ -0,0 +1,24 @@ +/* PR rtl-optimization/68376 */ + +int a, b, c = 1; +signed char d; + +int +main () +{ + for (; a < 1; a++) + for (; b < 1; b++) + { + signed char e = ~d; + if (d < 1) + e = d; + d = e; + if (!c) + __builtin_abort (); + } + + if (d != 0) + __builtin_abort (); + + return 0; +} --- gcc/testsuite/gcc.c-torture/execute/pr68376-2.c (revision 0) +++ gcc/testsuite/gcc.c-torture/execute/pr68376-2.c (revision 231526) @@ -0,0 +1,73 @@ +/* PR rtl-optimization/68376 */ + +extern void abort (void); + +__attribute__((noinline, noclone)) int +f1 (int x) +{ + return x < 0 ? ~x : x; +} + +__attribute__((noinline, noclone)) int +f2 (int x) +{ + return x < 0 ? x : ~x; +} + +__attribute__((noinline, noclone)) int +f3 (int x) +{ + return x <= 0 ? ~x : x; +} + +__attribute__((noinline, noclone)) int +f4 (int x) +{ + return x <= 0 ? x : ~x; +} + +__attribute__((noinline, noclone)) int +f5 (int x) +{ + return x >= 0 ? ~x : x; +} + +__attribute__((noinline, noclone)) int +f6 (int x) +{ + return x >= 0 ? x : ~x; +} + +__attribute__((noinline, noclone)) int +f7 (int x) +{ + return x > 0 ? ~x : x; +} + +__attribute__((noinline, noclone)) int +f8 (int x) +{ + return x > 0 ? x : ~x; +} + +int +main () +{ + if (f1 (5) != 5 || f1 (-5) != 4 || f1 (0) != 0) + abort (); + if (f2 (5) != -6 || f2 (-5) != -5 || f2 (0) != -1) + abort (); + if (f3 (5) != 5 || f3 (-5) != 4 || f3 (0) != -1) + abort (); + if (f4 (5) != -6 || f4 (-5) != -5 || f4 (0) != 0) + abort (); + if (f5 (5) != -6 || f5 (-5) != -5 || f5 (0) != -1) + abort (); + if (f6 (5) != 5 || f6 (-5) != 4 || f6 (0) != 0) + abort (); + if (f7 (5) != -6 || f7 (-5) != -5 || f7 (0) != 0) + abort (); + if (f8 (5) != 5 || f8 (-5) != 4 || f8 (0) != -1) + abort (); + return 0; +} --- gcc/testsuite/gcc.dg/pr68670-1.c (revision 0) +++ gcc/testsuite/gcc.dg/pr68670-1.c (revision 231526) @@ -0,0 +1,5 @@ +/* PR rtl-optimization/68670 */ +/* { dg-do run } */ +/* { dg-options "-O2 -ftracer" } */ + +#include "../gcc.c-torture/execute/pr68376-1.c" --- gcc/testsuite/gcc.dg/pr68670-2.c (revision 0) +++ gcc/testsuite/gcc.dg/pr68670-2.c (revision 231526) @@ -0,0 +1,5 @@ +/* PR rtl-optimization/68670 */ +/* { dg-do run } */ +/* { dg-options "-O2 -ftracer" } */ + +#include "../gcc.c-torture/execute/pr68376-2.c" 2016-02-11 Jakub Jelinek Backported from mainline 2016-01-01 Jakub Jelinek PR target/69015 * ifcvt.c (find_cond_trap): Give up if returnjump_p (jump). * gcc.dg/pr69015.c: New test. --- gcc/ifcvt.c (revision 232019) +++ gcc/ifcvt.c (revision 232020) @@ -4526,8 +4526,11 @@ find_cond_trap (basic_block test_bb, edg return FALSE; /* If the conditional jump is more than just a conditional jump, then - we can not do if-conversion on this block. */ - if (! onlyjump_p (jump)) + we can not do if-conversion on this block. Give up for returnjump_p, + changing a conditional return followed by unconditional trap for + conditional trap followed by unconditional return is likely not + beneficial and harder to handle. */ + if (! onlyjump_p (jump) || returnjump_p (jump)) return FALSE; /* We must be comparing objects whose modes imply the size. */ --- gcc/testsuite/gcc.dg/pr69015.c (revision 0) +++ gcc/testsuite/gcc.dg/pr69015.c (revision 232020) @@ -0,0 +1,10 @@ +/* PR target/69015 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -fno-if-conversion" } */ + +void +foo (int c) +{ + if (c) + __builtin_trap (); +} 2016-02-11 Jakub Jelinek Backported from mainline 2016-01-07 Jakub Jelinek PR middle-end/68960 * gimple-expr.c (copy_var_decl): If var has DECL_USER_ALIGN set, copy it and DECL_ALIGN too. * testsuite/libgomp.c/pr68960.c: New test. --- gcc/gimple-expr.c (revision 232121) +++ gcc/gimple-expr.c (revision 232122) @@ -375,6 +375,11 @@ copy_var_decl (tree var, tree name, tree TREE_USED (copy) = 1; DECL_SEEN_IN_BIND_EXPR_P (copy) = 1; DECL_ATTRIBUTES (copy) = DECL_ATTRIBUTES (var); + if (DECL_USER_ALIGN (var)) + { + DECL_ALIGN (copy) = DECL_ALIGN (var); + DECL_USER_ALIGN (copy) = 1; + } return copy; } --- libgomp/testsuite/libgomp.c/pr68960.c (revision 0) +++ libgomp/testsuite/libgomp.c/pr68960.c (revision 232122) @@ -0,0 +1,25 @@ +/* PR middle-end/68960 */ +/* { dg-do run } */ + +int +main () +{ + int temp[257] __attribute__ ((aligned (256))) = { 0 }; + #pragma omp parallel private (temp) num_threads (2) + { + int *p = &temp[0]; + asm volatile ("" : "+g" (p)); + if (((__UINTPTR_TYPE__) p) & 255) + __builtin_abort (); + } + #pragma omp parallel num_threads (2) + #pragma omp single + #pragma omp task firstprivate (temp) + { + int *p = &temp[0]; + asm volatile ("" : "+g" (p)); + if (((__UINTPTR_TYPE__) p) & 255) + __builtin_abort (); + } + return 0; +} 2016-02-11 Jakub Jelinek Backported from mainline 2016-01-08 Jakub Jelinek PR fortran/69128 * trans.h (OMPWS_SCALARIZER_BODY): Define. (OMPWS_NOWAIT): Renumber. * trans-stmt.c (gfc_trans_where_3): Only set OMPWS_SCALARIZER_WS if OMPWS_SCALARIZER_BODY is not set already, and set also OMPWS_SCALARIZER_BODY until the final loop creation. * trans-expr.c (gfc_trans_assignment_1): Likewise. * trans-openmp.c (gfc_trans_omp_workshare): Also clear OMPWS_SCALARIZER_BODY. * trans-array.c (gfc_trans_scalarized_loop_end): Don't create OMP_FOR if OMPWS_SCALARIZER_BODY is set. * gfortran.dg/gomp/pr69128.f90: New test. --- gcc/fortran/trans.h (revision 232150) +++ gcc/fortran/trans.h (revision 232151) @@ -1039,7 +1039,9 @@ extern const char gfc_msg_wrong_return[] construct is not workshared. */ #define OMPWS_SCALARIZER_WS 4 /* Set if scalarizer should attempt to create parallel loops. */ -#define OMPWS_NOWAIT 8 /* Use NOWAIT on OMP_FOR. */ +#define OMPWS_SCALARIZER_BODY 8 /* Set if handling body of potential + parallel loop. */ +#define OMPWS_NOWAIT 16 /* Use NOWAIT on OMP_FOR. */ extern int ompws_flags; #endif /* GFC_TRANS_H */ --- gcc/fortran/trans-stmt.c (revision 232150) +++ gcc/fortran/trans-stmt.c (revision 232151) @@ -5057,10 +5057,15 @@ gfc_trans_where_3 (gfc_code * cblock, gf gfc_loopinfo loop; gfc_ss *edss = 0; gfc_ss *esss = 0; + bool maybe_workshare = false; /* Allow the scalarizer to workshare simple where loops. */ - if (ompws_flags & OMPWS_WORKSHARE_FLAG) - ompws_flags |= OMPWS_SCALARIZER_WS; + if ((ompws_flags & (OMPWS_WORKSHARE_FLAG | OMPWS_SCALARIZER_BODY)) + == OMPWS_WORKSHARE_FLAG) + { + maybe_workshare = true; + ompws_flags |= OMPWS_SCALARIZER_WS | OMPWS_SCALARIZER_BODY; + } cond = cblock->expr1; tdst = cblock->next->expr1; @@ -5160,6 +5165,8 @@ gfc_trans_where_3 (gfc_code * cblock, gf gfc_add_expr_to_block (&body, tmp); gfc_add_block_to_block (&body, &cse.post); + if (maybe_workshare) + ompws_flags &= ~OMPWS_SCALARIZER_BODY; gfc_trans_scalarizing_loops (&loop, &body); gfc_add_block_to_block (&block, &loop.pre); gfc_add_block_to_block (&block, &loop.post); --- gcc/fortran/trans-expr.c (revision 232150) +++ gcc/fortran/trans-expr.c (revision 232151) @@ -9160,6 +9160,7 @@ gfc_trans_assignment_1 (gfc_expr * expr1 bool scalar_to_array; tree string_length; int n; + bool maybe_workshare = false; /* Assignment of the form lhs = rhs. */ gfc_start_block (&block); @@ -9234,8 +9235,13 @@ gfc_trans_assignment_1 (gfc_expr * expr1 } /* Allow the scalarizer to workshare array assignments. */ - if ((ompws_flags & OMPWS_WORKSHARE_FLAG) && loop.temp_ss == NULL) - ompws_flags |= OMPWS_SCALARIZER_WS; + if ((ompws_flags & (OMPWS_WORKSHARE_FLAG | OMPWS_SCALARIZER_BODY)) + == OMPWS_WORKSHARE_FLAG + && loop.temp_ss == NULL) + { + maybe_workshare = true; + ompws_flags |= OMPWS_SCALARIZER_WS | OMPWS_SCALARIZER_BODY; + } /* Start the scalarized loop body. */ gfc_start_scalarized_body (&loop, &body); @@ -9384,6 +9390,9 @@ gfc_trans_assignment_1 (gfc_expr * expr1 gfc_add_expr_to_block (&loop.code[expr1->rank - 1], tmp); } + if (maybe_workshare) + ompws_flags &= ~OMPWS_SCALARIZER_BODY; + /* Generate the copying loops. */ gfc_trans_scalarizing_loops (&loop, &body); --- gcc/fortran/trans-openmp.c (revision 232150) +++ gcc/fortran/trans-openmp.c (revision 232151) @@ -4297,7 +4297,7 @@ gfc_trans_omp_workshare (gfc_code *code, /* By default, every gfc_code is a single unit of work. */ ompws_flags |= OMPWS_CURR_SINGLEUNIT; - ompws_flags &= ~OMPWS_SCALARIZER_WS; + ompws_flags &= ~(OMPWS_SCALARIZER_WS | OMPWS_SCALARIZER_BODY); switch (code->op) { --- gcc/fortran/trans-array.c (revision 232150) +++ gcc/fortran/trans-array.c (revision 232151) @@ -3601,7 +3601,8 @@ gfc_trans_scalarized_loop_end (gfc_loopi tree init; tree incr; - if ((ompws_flags & (OMPWS_WORKSHARE_FLAG | OMPWS_SCALARIZER_WS)) + if ((ompws_flags & (OMPWS_WORKSHARE_FLAG | OMPWS_SCALARIZER_WS + | OMPWS_SCALARIZER_BODY)) == (OMPWS_WORKSHARE_FLAG | OMPWS_SCALARIZER_WS) && n == loop->dimen - 1) { --- gcc/testsuite/gfortran.dg/gomp/pr69128.f90 (revision 0) +++ gcc/testsuite/gfortran.dg/gomp/pr69128.f90 (revision 232151) @@ -0,0 +1,23 @@ +! PR fortran/69128 +! { dg-do compile } + +program test + implicit none + interface + subroutine use(b, c) + real, allocatable :: b(:), c(:) + end subroutine + end interface + real, allocatable :: a(:,:), b(:), c(:) + integer :: dim1, dim2, i,j + dim1=10000 + dim2=500 + allocate(a(dim1,dim2),b(dim1),c(dim1)) + call random_number(a) + +!$omp parallel workshare + b(:) = maxval(a(:,:), dim=2) + c(:) = sum(a(:,:), dim=2) +!$omp end parallel workshare + call use(b, c) +end program 2016-02-11 Jakub Jelinek Backported from mainline 2016-01-11 Jakub Jelinek PR tree-optimization/69214 * tree-vrp.c (simplify_cond_using_ranges): Don't propagate innerop into a comparison if SSA_NAME_OCCURS_IN_ABNORMAL_PHI. Formatting fix. * gcc.c-torture/compile/pr69214.c: New test. --- gcc/tree-vrp.c (revision 232234) +++ gcc/tree-vrp.c (revision 232235) @@ -9534,7 +9534,8 @@ simplify_cond_using_ranges (gcond *stmt) innerop = gimple_assign_rhs1 (def_stmt); if (TREE_CODE (innerop) == SSA_NAME - && !POINTER_TYPE_P (TREE_TYPE (innerop))) + && !POINTER_TYPE_P (TREE_TYPE (innerop)) + && !SSA_NAME_OCCURS_IN_ABNORMAL_PHI (innerop)) { value_range_t *vr = get_value_range (innerop); @@ -9565,8 +9566,8 @@ simplify_cond_using_ranges (gcond *stmt) else location = gimple_location (stmt); warning_at (location, OPT_Wstrict_overflow, - "assuming signed overflow does not occur when " - "simplifying conditional"); + "assuming signed overflow does not occur when " + "simplifying conditional"); } tree newconst = fold_convert (TREE_TYPE (innerop), op1); --- gcc/testsuite/gcc.c-torture/compile/pr69214.c (revision 0) +++ gcc/testsuite/gcc.c-torture/compile/pr69214.c (revision 232235) @@ -0,0 +1,17 @@ +/* PR tree-optimization/69214 */ + +extern void bar (void); +extern int __setjmp (char *); + +void +foo (char *p) +{ + int d = 0; + bar (); + if (__setjmp (p)) + return; + long a = d; + d = 8; + if (!a) + bar (); +} 2016-02-11 Jakub Jelinek Backported from mainline 2016-01-19 Jakub Jelinek PR rtl-optimization/68955 PR rtl-optimization/64557 * dse.c (record_store, check_mem_read_rtx): Don't call get_addr here. Fix up formatting. * alias.c (get_addr): Handle VALUE +/- CONST_SCALAR_INT_P. * gcc.dg/torture/pr68955.c: New test. --- gcc/dse.c (revision 232553) +++ gcc/dse.c (revision 232554) @@ -1571,14 +1571,9 @@ record_store (rtx body, bb_info_t bb_inf mem_addr = base->val_rtx; else { - group_info_t group - = rtx_group_vec[group_id]; + group_info_t group = rtx_group_vec[group_id]; mem_addr = group->canon_base_addr; } - /* get_addr can only handle VALUE but cannot handle expr like: - VALUE + OFFSET, so call get_addr to get original addr for - mem_addr before plus_constant. */ - mem_addr = get_addr (mem_addr); if (offset) mem_addr = plus_constant (get_address_mode (mem), mem_addr, offset); } @@ -2188,14 +2183,9 @@ check_mem_read_rtx (rtx *loc, bb_info_t mem_addr = base->val_rtx; else { - group_info_t group - = rtx_group_vec[group_id]; + group_info_t group = rtx_group_vec[group_id]; mem_addr = group->canon_base_addr; } - /* get_addr can only handle VALUE but cannot handle expr like: - VALUE + OFFSET, so call get_addr to get original addr for - mem_addr before plus_constant. */ - mem_addr = get_addr (mem_addr); if (offset) mem_addr = plus_constant (get_address_mode (mem), mem_addr, offset); } --- gcc/alias.c (revision 232553) +++ gcc/alias.c (revision 232554) @@ -2193,8 +2193,8 @@ refs_newer_value_p (const_rtx expr, rtx } /* Convert the address X into something we can use. This is done by returning - it unchanged unless it is a value; in the latter case we call cselib to get - a more useful rtx. */ + it unchanged unless it is a VALUE or VALUE +/- constant; for VALUE + we call cselib to get a more useful rtx. */ rtx get_addr (rtx x) @@ -2203,7 +2203,23 @@ get_addr (rtx x) struct elt_loc_list *l; if (GET_CODE (x) != VALUE) - return x; + { + if ((GET_CODE (x) == PLUS || GET_CODE (x) == MINUS) + && GET_CODE (XEXP (x, 0)) == VALUE + && CONST_SCALAR_INT_P (XEXP (x, 1))) + { + rtx op0 = get_addr (XEXP (x, 0)); + if (op0 != XEXP (x, 0)) + { + if (GET_CODE (x) == PLUS + && GET_CODE (XEXP (x, 1)) == CONST_INT) + return plus_constant (GET_MODE (x), op0, INTVAL (XEXP (x, 1))); + return simplify_gen_binary (GET_CODE (x), GET_MODE (x), + op0, XEXP (x, 1)); + } + } + return x; + } v = CSELIB_VAL_PTR (x); if (v) { --- gcc/testsuite/gcc.dg/torture/pr68955.c (revision 0) +++ gcc/testsuite/gcc.dg/torture/pr68955.c (revision 232554) @@ -0,0 +1,41 @@ +/* PR rtl-optimization/68955 */ +/* { dg-do run } */ +/* { dg-output "ONE1ONE" } */ + +int a, b, c, d, g, m; +int i[7][7][5] = { { { 5 } }, { { 5 } }, + { { 5 }, { 5 }, { 5 }, { 5 }, { 5 }, { -1 } } }; +static int j = 11; +short e, f, h, k, l; + +static void +foo () +{ + for (; e < 5; e++) + for (h = 3; h; h--) + { + for (g = 1; g < 6; g++) + { + m = c == 0 ? b : b / c; + i[e][1][e] = i[1][1][1] | (m & l) && f; + } + for (k = 0; k < 6; k++) + { + for (d = 0; d < 6; d++) + i[1][e][h] = i[h][k][e] >= l; + i[e + 2][h + 3][e] = 6 & l; + i[2][1][2] = a; + for (; j < 5;) + for (;;) + ; + } + } +} + +int +main () +{ + foo (); + __builtin_printf ("ONE%dONE\n", i[1][0][2]); + return 0; +} 2016-02-11 Jakub Jelinek Backported from mainline 2016-01-21 Jakub Jelinek PR middle-end/67653 * gimplify.c (gimplify_asm_expr): Warn if it is too late to attempt to mark memory input operand addressable and call prepare_gimple_addressable in that case. Don't adjust input_location for diagnostics, use error_at instead. * c-c++-common/pr67653.c: New test. * gcc.dg/torture/pr29119.c: Add dg-warning. --- gcc/gimplify.c (revision 232639) +++ gcc/gimplify.c (revision 232640) @@ -5305,12 +5305,38 @@ gimplify_asm_expr (tree *expr_p, gimple_ TREE_VALUE (link) = error_mark_node; tret = gimplify_expr (&TREE_VALUE (link), pre_p, post_p, is_gimple_lvalue, fb_lvalue | fb_mayfail); + if (tret != GS_ERROR) + { + /* Unlike output operands, memory inputs are not guaranteed + to be lvalues by the FE, and while the expressions are + marked addressable there, if it is e.g. a statement + expression, temporaries in it might not end up being + addressable. They might be already used in the IL and thus + it is too late to make them addressable now though. */ + tree x = TREE_VALUE (link); + while (handled_component_p (x)) + x = TREE_OPERAND (x, 0); + if (TREE_CODE (x) == MEM_REF + && TREE_CODE (TREE_OPERAND (x, 0)) == ADDR_EXPR) + x = TREE_OPERAND (TREE_OPERAND (x, 0), 0); + if ((TREE_CODE (x) == VAR_DECL + || TREE_CODE (x) == PARM_DECL + || TREE_CODE (x) == RESULT_DECL) + && !TREE_ADDRESSABLE (x) + && is_gimple_reg (x)) + { + warning_at (EXPR_LOC_OR_LOC (TREE_VALUE (link), + input_location), 0, + "memory input %d is not directly addressable", + i); + prepare_gimple_addressable (&TREE_VALUE (link), pre_p); + } + } mark_addressable (TREE_VALUE (link)); if (tret == GS_ERROR) { - if (EXPR_HAS_LOCATION (TREE_VALUE (link))) - input_location = EXPR_LOCATION (TREE_VALUE (link)); - error ("memory input %d is not directly addressable", i); + error_at (EXPR_LOC_OR_LOC (TREE_VALUE (link), input_location), + "memory input %d is not directly addressable", i); ret = tret; } } --- gcc/testsuite/gcc.dg/torture/pr29119.c (revision 232639) +++ gcc/testsuite/gcc.dg/torture/pr29119.c (revision 232640) @@ -2,6 +2,5 @@ void ldt_add_entry(void) { - __asm__ ("" :: "m"(({unsigned __v; __v;}))); + __asm__ ("" :: "m"(({unsigned __v; __v;}))); /* { dg-warning "memory input 0 is not directly addressable" } */ } - --- gcc/testsuite/c-c++-common/pr67653.c (revision 0) +++ gcc/testsuite/c-c++-common/pr67653.c (revision 232640) @@ -0,0 +1,8 @@ +/* PR middle-end/67653 */ +/* { dg-do compile } */ + +void +foo (void) +{ + __asm__ ("" : : "m" (({ static int a; a; }))); /* { dg-warning "memory input 0 is not directly addressable" } */ +} 2016-02-11 Jakub Jelinek Backported from mainline 2016-01-22 Jakub Jelinek PR target/69432 * config/i386/i386.c (expand_small_movmem_or_setmem, expand_set_or_movmem_prologue_epilogue_by_misaligned_moves): Spelling fixes. (ix86_expand_set_or_movmem): Call do_pending_stack_adjust () early if dynamic_check != -1. * g++.dg/opt/pr69432.C: New test. --- gcc/config/i386/i386.c (revision 232753) +++ gcc/config/i386/i386.c (revision 232754) @@ -24376,7 +24377,7 @@ expand_small_movmem_or_setmem (rtx destm if (DYNAMIC_CHECK) Round COUNT down to multiple of SIZE << optional caller supplied zero size guard is here >> - << optional caller suppplied dynamic check is here >> + << optional caller supplied dynamic check is here >> << caller supplied main copy loop is here >> } done_label: @@ -24550,8 +24551,8 @@ expand_set_or_movmem_prologue_epilogue_b else *min_size = 0; - /* Our loops always round down the bock size, but for dispatch to library - we need precise value. */ + /* Our loops always round down the block size, but for dispatch to + library we need precise value. */ if (dynamic_check) *count = expand_simple_binop (GET_MODE (*count), AND, *count, GEN_INT (-size), *count, 1, OPTAB_DIRECT); @@ -25129,6 +25130,13 @@ ix86_expand_set_or_movmem (rtx dst, rtx size_needed = GET_MODE_SIZE (move_mode) * unroll_factor; epilogue_size_needed = size_needed; + /* If we are going to call any library calls conditionally, make sure any + pending stack adjustment happen before the first conditional branch, + otherwise they will be emitted before the library call only and won't + happen from the other branches. */ + if (dynamic_check != -1) + do_pending_stack_adjust (); + desired_align = decide_alignment (align, alg, expected_size, move_mode); if (!TARGET_ALIGN_STRINGOPS || noalign) align = desired_align; --- gcc/testsuite/g++.dg/opt/pr69432.C (revision 0) +++ gcc/testsuite/g++.dg/opt/pr69432.C (revision 232754) @@ -0,0 +1,62 @@ +// PR target/69432 +// { dg-do compile } +// { dg-options "-O3" } +// { dg-additional-options "-minline-stringops-dynamically" { target i?86-*-* x86_64-*-* } } + +template +void +f1 (S x, T y, U z) +{ + for (; y; --y, ++x) + *x = z; +} + +template +void f2 (S x, T y, U z) +{ + f1 (x, y, z); +} + +struct A {}; +struct B { static char f3 (A, unsigned); }; + +template +void f4 (S, U); + +struct C +{ + template + static S f5 (S x, T y, U z) { f2 (x, y, z); } +}; + +template +void f6 (S x, T y, U z) { C::f5 (x, y, z); } + +template +void f7 (S x, T y, U z, V) { f6 (x, y, z); } + +struct E +{ + struct D : A { char e; D (A); }; + A f; + E (int x) : g(f) { f8 (x); } + ~E (); + D g; + void f9 (int x) { x ? B::f3 (g, x) : char (); } + void f8 (int x) { f9 (x); } +}; + +struct F : E +{ + F (int x) : E(x) { f10 (x); f4 (this, 0); } + char h; + void f10 (int x) { f7 (&g.e, x, h, 0); } +}; + +long a; + +void +test () +{ + F b(a); +} 2016-02-11 Jakub Jelinek Backported from mainline 2016-01-28 Jakub Jelinek PR pch/68176 * files.c (_cpp_find_file): Set file->implicit_preinclude even if included from file->implicit_preinclude header. --- libcpp/files.c (revision 232955) +++ libcpp/files.c (revision 232956) @@ -522,7 +522,10 @@ _cpp_find_file (cpp_reader *pfile, const return entry->u.file; file = make_cpp_file (pfile, start_dir, fname); - file->implicit_preinclude = implicit_preinclude; + file->implicit_preinclude + = (implicit_preinclude + || (pfile->buffer + && pfile->buffer->file->implicit_preinclude)); /* Try each path in the include chain. */ for (; !fake ;) 2016-02-11 Jakub Jelinek Backported from mainline 2016-02-08 Jakub Jelinek PR c++/59627 * parser.c (cp_parser_omp_declare_reduction): Set assembler name of the DECL_OMP_DECLARE_REDUCTION_P decls. * g++.dg/gomp/pr59627.C: New test. --- gcc/cp/parser.c (revision 233224) +++ gcc/cp/parser.c (revision 233225) @@ -36080,6 +36080,7 @@ cp_parser_omp_declare_reduction (cp_pars DECL_DECLARED_INLINE_P (fndecl) = 1; DECL_IGNORED_P (fndecl) = 1; DECL_OMP_DECLARE_REDUCTION_P (fndecl) = 1; + SET_DECL_ASSEMBLER_NAME (fndecl, get_identifier ("")); DECL_ATTRIBUTES (fndecl) = tree_cons (get_identifier ("gnu_inline"), NULL_TREE, DECL_ATTRIBUTES (fndecl)); --- gcc/testsuite/g++.dg/gomp/pr59627.C (revision 0) +++ gcc/testsuite/g++.dg/gomp/pr59627.C (revision 233225) @@ -0,0 +1,14 @@ +// PR c++/59627 +// { dg-do compile { target lto } } +// { dg-options "-fopenmp -flto" } + +struct A { A () : i (0) {} int i; }; + +void +foo () +{ + A a; + #pragma omp declare reduction (+: A: omp_out.i += omp_in.i) + #pragma omp parallel reduction (+: a) + ; +} --- libcpp/include/cpplib.h (revision 230590) +++ libcpp/include/cpplib.h (revision 230591) @@ -986,6 +986,9 @@ extern bool cpp_warning_syshdr (cpp_read /* Output a diagnostic with "MSGID: " preceding the error string of errno. No location is printed. */ extern bool cpp_errno (cpp_reader *, int, const char *msgid); +/* Similarly, but with "FILENAME: " instead of "MSGID: ", where + the filename is not localized. */ +extern bool cpp_errno_filename (cpp_reader *, int, const char *filename); /* Same as cpp_error, except additionally specifies a position as a (translation unit) physical line and physical column. If the line is --- libcpp/files.c (revision 230590) +++ libcpp/files.c (revision 230591) @@ -715,7 +715,7 @@ read_file_guts (cpp_reader *pfile, _cpp_ if (count < 0) { - cpp_errno (pfile, CPP_DL_ERROR, file->path); + cpp_errno_filename (pfile, CPP_DL_ERROR, file->path); free (buf); return false; } @@ -1053,7 +1053,8 @@ open_file_failed (cpp_reader *pfile, _cp /* If the preprocessor output (other than dependency information) is being used, we must also flag an error. */ if (CPP_OPTION (pfile, deps.need_preprocessor_output)) - cpp_errno (pfile, CPP_DL_FATAL, file->path); + cpp_errno_filename (pfile, CPP_DL_FATAL, + file->path ? file->path : file->name); } else { @@ -1067,9 +1068,11 @@ open_file_failed (cpp_reader *pfile, _cp if (CPP_OPTION (pfile, deps.style) == DEPS_NONE || print_dep || CPP_OPTION (pfile, deps.need_preprocessor_output)) - cpp_errno (pfile, CPP_DL_FATAL, file->path); + cpp_errno_filename (pfile, CPP_DL_FATAL, + file->path ? file->path : file->name); else - cpp_errno (pfile, CPP_DL_WARNING, file->path); + cpp_errno_filename (pfile, CPP_DL_WARNING, + file->path ? file->path : file->name); } } --- libcpp/errors.c (revision 230590) +++ libcpp/errors.c (revision 230591) @@ -230,8 +230,18 @@ cpp_warning_with_line_syshdr (cpp_reader bool cpp_errno (cpp_reader *pfile, int level, const char *msgid) { - if (msgid[0] == '\0') - msgid = _("stdout"); + return cpp_error (pfile, level, "%s: %s", _(msgid), xstrerror (errno)); +} + +/* Print a warning or error, depending on the value of LEVEL. Include + information from errno. Unlike cpp_errno, the argument is a filename + that is not localized, but "" is replaced with localized "stdout". */ + +bool +cpp_errno_filename (cpp_reader *pfile, int level, const char *filename) +{ + if (filename[0] == '\0') + filename = _("stdout"); - return cpp_error (pfile, level, "%s: %s", msgid, xstrerror (errno)); + return cpp_error (pfile, level, "%s: %s", filename, xstrerror (errno)); }