From patchwork Wed Feb 27 20:18:14 2013 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Jakub Jelinek X-Patchwork-Id: 223693 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]) by ozlabs.org (Postfix) with SMTP id 051BB2C0040 for ; Thu, 28 Feb 2013 07:18:32 +1100 (EST) Comment: DKIM? See http://www.dkim.org DKIM-Signature: v=1; a=rsa-sha1; c=relaxed/relaxed; d=gcc.gnu.org; s=default; x=1362601113; h=Comment: DomainKey-Signature:Received:Received:Received:Received:Received: Received:Received:Date:From:To:Cc:Subject:Message-ID:Reply-To: MIME-Version:Content-Type:Content-Disposition:User-Agent: Mailing-List:Precedence:List-Id:List-Unsubscribe:List-Archive: List-Post:List-Help:Sender:Delivered-To; bh=bX/knJY/Ycr1zylFvK/f 9Lr1FqM=; b=BwD3Vv90ROuJbuSjz9vj4NplsBuJoY4W05O/7uDYKo43RUmvJm/a XvFT+XKF6vbmkk8RUxivwgZqIRrmOLLa6HPyJah0jm+KSeMFRytxrkCDfbWCoLy2 45SPtJ0ES213dcHhEfDqjlasClt8J4j1KUjKEJuPmDOCRGt/Tqqq1EM= Comment: DomainKeys? See http://antispam.yahoo.com/domainkeys DomainKey-Signature: a=rsa-sha1; q=dns; c=nofws; s=default; d=gcc.gnu.org; h=Received:Received:X-SWARE-Spam-Status:X-Spam-Check-By:Received:Received:Received:Received:Received:Date:From:To:Cc:Subject:Message-ID:Reply-To:MIME-Version:Content-Type:Content-Disposition:User-Agent:X-IsSubscribed:Mailing-List:Precedence:List-Id:List-Unsubscribe:List-Archive:List-Post:List-Help:Sender:Delivered-To; b=cqmkc88krelPs2zHNPF1tiP/OqsGz8ih9i33mzVtoQkbVgmRMSabfLBufVm8lb xjkowHDOy0z14ZTwqFUCN+23RXv6I0qshN0dQQaarFoqMJVUaiTC/aVkiCgvAUCY R5VwsdXWMMe2gxVHxefRVob6LRN9yx2GXPcLFoEAQD6mU=; Received: (qmail 31635 invoked by alias); 27 Feb 2013 20:18:27 -0000 Received: (qmail 31620 invoked by uid 22791); 27 Feb 2013 20:18:26 -0000 X-SWARE-Spam-Status: No, hits=-6.6 required=5.0 tests=AWL, BAYES_00, KHOP_RCVD_UNTRUST, KHOP_SPAMHAUS_DROP, RCVD_IN_DNSWL_HI, RCVD_IN_HOSTKARMA_W, RP_MATCHES_RCVD, SPF_HELO_PASS X-Spam-Check-By: sourceware.org Received: from mx1.redhat.com (HELO mx1.redhat.com) (209.132.183.28) by sourceware.org (qpsmtpd/0.43rc1) with ESMTP; Wed, 27 Feb 2013 20:18:17 +0000 Received: from int-mx10.intmail.prod.int.phx2.redhat.com (int-mx10.intmail.prod.int.phx2.redhat.com [10.5.11.23]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r1RKIHt6021083 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK) for ; Wed, 27 Feb 2013 15:18:17 -0500 Received: from zalov.cz (vpn1-4-213.ams2.redhat.com [10.36.4.213]) by int-mx10.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r1RKIFDT011047 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=NO); Wed, 27 Feb 2013 15:18:17 -0500 Received: from zalov.cz (localhost [127.0.0.1]) by zalov.cz (8.14.5/8.14.5) with ESMTP id r1RKIESS017695; Wed, 27 Feb 2013 21:18:15 +0100 Received: (from jakub@localhost) by zalov.cz (8.14.5/8.14.5/Submit) id r1RKIEf2017694; Wed, 27 Feb 2013 21:18:14 +0100 Date: Wed, 27 Feb 2013 21:18:14 +0100 From: Jakub Jelinek To: Tom Tromey Cc: gcc-patches@gcc.gnu.org Subject: [PATCH] Fix up _cpp_find_file Message-ID: <20130227201814.GO12913@tucnak.redhat.com> Reply-To: Jakub Jelinek MIME-Version: 1.0 Content-Disposition: inline User-Agent: Mutt/1.5.21 (2010-09-15) X-IsSubscribed: yes 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 Hi! As discussed on IRC, this function calls htab_find_slot_with_hash with INSERT early, but sometimes decides to return without actually making sure *hash_slot is non-NULL. That can result in broken hash table, because NULL is empty entry and could break lookup for some other hash value. Fixed by calling htab_clear_slot. Also, I think it is an aliasing violation to access *hash_slot through a different type than the one hashtab.c accesses it through (void *), so I've fixed that too. Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk? 2013-02-27 Jakub Jelinek * files.c (_cpp_find_file): If returning early, before storing something to *hash_slot and *hash_slot is NULL, call htab_clear_slot on it. Access *hash_slot using void * type rather than struct file_hash_entry * to avoid aliasing issues. Jakub --- gcc/files.c.jj 2013-01-15 09:04:55.000000000 +0100 +++ gcc/files.c 2013-02-27 16:31:50.000912853 +0100 @@ -492,7 +492,8 @@ _cpp_file * _cpp_find_file (cpp_reader *pfile, const char *fname, cpp_dir *start_dir, bool fake, int angle_brackets, bool implicit_preinclude) { - struct file_hash_entry *entry, **hash_slot; + struct file_hash_entry *entry; + void **hash_slot; _cpp_file *file; bool invalid_pch = false; bool saw_bracket_include = false; @@ -503,13 +504,12 @@ _cpp_find_file (cpp_reader *pfile, const if (start_dir == NULL) cpp_error (pfile, CPP_DL_ICE, "NULL directory in find_file"); - hash_slot = (struct file_hash_entry **) - htab_find_slot_with_hash (pfile->file_hash, fname, - htab_hash_string (fname), - INSERT); + hash_slot + = htab_find_slot_with_hash (pfile->file_hash, fname, + htab_hash_string (fname), INSERT); /* First check the cache before we resort to memory allocation. */ - entry = search_cache (*hash_slot, start_dir); + entry = search_cache ((struct file_hash_entry *) *hash_slot, start_dir); if (entry) return entry->u.file; @@ -533,6 +533,17 @@ _cpp_find_file (cpp_reader *pfile, const the list of all files so that #import works. */ file->next_file = pfile->all_files; pfile->all_files = file; + if (*hash_slot == NULL) + { + /* If *hash_slot is NULL, the above htab_find_slot_with_hash + call just created the slot, but we aren't going to store + there anything, so need to remove the newly created entry. + htab_clear_slot requires that it is non-NULL, so store + there some non-NULL pointer, htab_clear_slot will + overwrite it immediately. */ + *hash_slot = file; + htab_clear_slot (pfile->file_hash, hash_slot); + } return file; } @@ -548,6 +559,12 @@ _cpp_find_file (cpp_reader *pfile, const { free ((char *) file->name); free (file); + if (*hash_slot == NULL) + { + /* See comment on the above htab_clear_slot call. */ + *hash_slot = file; + htab_clear_slot (pfile->file_hash, hash_slot); + } return NULL; } else @@ -565,7 +582,7 @@ _cpp_find_file (cpp_reader *pfile, const else continue; - entry = search_cache (*hash_slot, file->dir); + entry = search_cache ((struct file_hash_entry *) *hash_slot, file->dir); if (entry) { found_in_cache = file->dir; @@ -589,11 +606,11 @@ _cpp_find_file (cpp_reader *pfile, const /* Store this new result in the hash table. */ entry = new_file_hash_entry (pfile); - entry->next = *hash_slot; + entry->next = (struct file_hash_entry *) *hash_slot; entry->start_dir = start_dir; entry->location = pfile->line_table->highest_location; entry->u.file = file; - *hash_slot = entry; + *hash_slot = (void *) entry; /* If we passed the quote or bracket chain heads, cache them also. This speeds up processing if there are lots of -I options. */ @@ -602,22 +619,22 @@ _cpp_find_file (cpp_reader *pfile, const && found_in_cache != pfile->bracket_include) { entry = new_file_hash_entry (pfile); - entry->next = *hash_slot; + entry->next = (struct file_hash_entry *) *hash_slot; entry->start_dir = pfile->bracket_include; entry->location = pfile->line_table->highest_location; entry->u.file = file; - *hash_slot = entry; + *hash_slot = (void *) entry; } if (saw_quote_include && pfile->quote_include != start_dir && found_in_cache != pfile->quote_include) { entry = new_file_hash_entry (pfile); - entry->next = *hash_slot; + entry->next = (struct file_hash_entry *) *hash_slot; entry->start_dir = pfile->quote_include; entry->location = pfile->line_table->highest_location; entry->u.file = file; - *hash_slot = entry; + *hash_slot = (void *) entry; } return file;