From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 102577 invoked by alias); 18 Mar 2015 19:39:30 -0000 Mailing-List: contact gdb-patches-help@sourceware.org; run by ezmlm Precedence: bulk List-Id: List-Subscribe: List-Archive: List-Post: List-Help: , Sender: gdb-patches-owner@sourceware.org Received: (qmail 102447 invoked by uid 89); 18 Mar 2015 19:39:29 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=-1.8 required=5.0 tests=AWL,BAYES_00,SPF_HELO_PASS,SPF_PASS,T_RP_MATCHES_RCVD autolearn=ham version=3.3.2 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; Wed, 18 Mar 2015 19:39:23 +0000 Received: from int-mx09.intmail.prod.int.phx2.redhat.com (int-mx09.intmail.prod.int.phx2.redhat.com [10.5.11.22]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id t2IJdMJV008272 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-GCM-SHA384 bits=256 verify=FAIL) for ; Wed, 18 Mar 2015 15:39:22 -0400 Received: from psique.redhat.com (ovpn-113-183.phx2.redhat.com [10.3.113.183]) by int-mx09.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id t2IJdJ9N007817; Wed, 18 Mar 2015 15:39:21 -0400 From: Sergio Durigan Junior To: GDB Patches Cc: Pedro Alves , Sergio Durigan Junior Subject: [PATCH 2/4] Update gcore_create_callback to better handle different states of mappings Date: Wed, 18 Mar 2015 19:39:00 -0000 Message-Id: <1426707523-6499-3-git-send-email-sergiodj@redhat.com> In-Reply-To: <1426707523-6499-1-git-send-email-sergiodj@redhat.com> References: <1426707523-6499-1-git-send-email-sergiodj@redhat.com> X-IsSubscribed: yes X-SW-Source: 2015-03/txt/msg00558.txt.bz2 This patch updates gdb/gcore.c's gcore_create_callback function and changes its logic to improve the handling of different states of memory mappings. One of the major modifications is that mappings marked as UNMODIFIED are now completely ignored by the function (i.e., not even the segment headers are created anymore). This is now possible because of the introduction of the new UNKNOWN state (see below). We now know that when the mapping is UNMODIFIED, it means that the user has either chose to ignore it via /proc/PID/coredump_filter, or that it is marked as VM_DONTDUMP (and therefore should not be dumped anyway). This is what the Linux kernel does, too. The new UNKNOWN state is being used to identify situations when we don't really know whether the mapping should be dumped or not. Based on that, we run an existing heuristic responsible for deciding if we should include the mapping's contents or not. One last thing worth mentioning is that this check: if (read == 0 && write == 0 && exec == 0 && modified_state == MEMORY_MAPPING_UNMODIFIED) has been simplified to: if (read == 0) This is because if the mapping has not 'read' permission set, it does not make sense to include its contents in the corefile (GDB would actually not be allowed to do that). Therefore, we just create a segment header for it. The Linux kernel differs from GDB here because it actually include the contents of this mapping in the corefile, but this is because it can read its contents. Changes from v2: - Return immediately if modified_state == MEMORY_MAPPING_UNMODIFIED - Improve comments explaining the case above, and also the case when "read == 0". gdb/ChangeLog: 2015-03-18 Sergio Durigan Junior Jan Kratochvil Oleg Nesterov PR corefiles/16092 * gcore.c (gcore_create_callback): Update code to handle the case when 'modified_state == MEMORY_MAPPING_UNMODIFIED'. Simplify condition used to decide when to create only a segment header for the mapping. Improve check to decide when to run a heuristic to decide whether to dump the mapping's contents. --- gdb/gcore.c | 39 +++++++++++++++++++++++++-------------- 1 file changed, 25 insertions(+), 14 deletions(-) diff --git a/gdb/gcore.c b/gdb/gcore.c index 751ddac..8dfcc02 100644 --- a/gdb/gcore.c +++ b/gdb/gcore.c @@ -422,23 +422,34 @@ gcore_create_callback (CORE_ADDR vaddr, unsigned long size, int read, asection *osec; flagword flags = SEC_ALLOC | SEC_HAS_CONTENTS | SEC_LOAD; - /* If the memory segment has no permissions set, ignore it, otherwise - when we later try to access it for read/write, we'll get an error - or jam the kernel. */ - if (read == 0 && write == 0 && exec == 0 - && modified_state == MEMORY_MAPPING_UNMODIFIED) + if (modified_state == MEMORY_MAPPING_UNMODIFIED) { - if (info_verbose) - { - fprintf_filtered (gdb_stdout, "Ignore segment, %s bytes at %s\n", - plongest (size), paddress (target_gdbarch (), vaddr)); - } - + /* When the memory mapping is marked as unmodified, this means + that it should not be included in the coredump file (either + because it was marked as VM_DONTDUMP, or because the user + explicitly chose to ignore it using the + /proc/PID/coredump_filter mechanism). + + We could in theory create a section header for it (i.e., mark + it as '~(SEC_LOAD | SEC_HAS_CONTENTS)', just like we do when + the mapping does not have the 'read' permission set), but the + Linux kernel itself ignores these mappings, and so do we. */ return 0; } - - if (write == 0 && modified_state == MEMORY_MAPPING_UNMODIFIED - && !solib_keep_data_in_core (vaddr, size)) + else if (read == 0) + { + /* If the memory segment has no read permission set, then we have to + generate a segment header for it, but without contents (i.e., + FileSiz = 0), otherwise when we later try to access it for + read/write, we'll get an error or jam the kernel. + + The Linux kernel differs from GDB in this point because it + can actually read this mapping, so it dumps this mapping's + contents in the corefile. */ + flags &= ~(SEC_LOAD | SEC_HAS_CONTENTS); + } + else if (write == 0 && modified_state == MEMORY_MAPPING_UNKNOWN_STATE + && !solib_keep_data_in_core (vaddr, size)) { /* See if this region of memory lies inside a known file on disk. If so, we can avoid copying its contents by clearing SEC_LOAD. */ -- 1.9.3