From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: (qmail 1774 invoked by alias); 9 Jan 2013 17:10:53 -0000 Received: (qmail 1753 invoked by uid 22791); 9 Jan 2013 17:10:51 -0000 X-SWARE-Spam-Status: No, hits=-7.7 required=5.0 tests=AWL,BAYES_00,KHOP_RCVD_UNTRUST,KHOP_THREADED,RCVD_IN_DNSWL_HI,RCVD_IN_HOSTKARMA_W,RP_MATCHES_RCVD,SPF_HELO_PASS,TW_QW 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, 09 Jan 2013 17:10:44 +0000 Received: from int-mx12.intmail.prod.int.phx2.redhat.com (int-mx12.intmail.prod.int.phx2.redhat.com [10.5.11.25]) by mx1.redhat.com (8.14.4/8.14.4) with ESMTP id r09HAgj0022219 (version=TLSv1/SSLv3 cipher=DHE-RSA-AES256-SHA bits=256 verify=OK); Wed, 9 Jan 2013 12:10:42 -0500 Received: from [127.0.0.1] (ovpn01.gateway.prod.ext.ams2.redhat.com [10.39.146.11]) by int-mx12.intmail.prod.int.phx2.redhat.com (8.14.4/8.14.4) with ESMTP id r09HAcRf003700; Wed, 9 Jan 2013 12:10:40 -0500 Message-ID: <50EDA48E.2030406@redhat.com> Date: Wed, 09 Jan 2013 17:10:00 -0000 From: Pedro Alves User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:17.0) Gecko/17.0 Thunderbird/17.0 MIME-Version: 1.0 To: Tristan Gingold CC: Joel Brobecker , gdb-patches@sourceware.org Subject: Re: [RFA/commit+doco 2/2] Windows x64 SEH unwinder. References: <1357728781-15073-1-git-send-email-brobecker@adacore.com> <1357728781-15073-3-git-send-email-brobecker@adacore.com> <50ED9221.1050504@redhat.com> <9E84DF2D-7AF8-4AA1-A5DF-171EF189A6E7@adacore.com> In-Reply-To: <9E84DF2D-7AF8-4AA1-A5DF-171EF189A6E7@adacore.com> Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit 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 X-SW-Source: 2013-01/txt/msg00173.txt.bz2 On 01/09/2013 04:28 PM, Tristan Gingold wrote: >>> I don't really see a real way of supporting both old and new versions >>> of GCC, unless we have a way of more finely ordering the unwinders. >> >> What specific finer order where you considering would be needed to >> fix this? > > Joel once proposed to activate this unwinder if the CU is compiled > by gcc 4.6 or older. I don't think you need to have a way of more finely ordering the unwinders for that. AFAICS, we can make the sniffer return false in that case. I had understood him as meaning something about making the whole prepend/append mechanisms more finer grained somehow. Checking the CU/producer is kind of the obvious choice. It requires debug info though. >> Maybe detect if the whole module (exe/dll) the PC points at >> contains any SEH (even if not for PC), and skip the SEH unwinder >> if not? Is that possible? > > Yes, but useless. There are SEH info in crt0. You mean, the parts that are in mingw, right? I'd assume any bits in gcc to only contain SEH in >=4.7. Yeah, seems like that wouldn't work for static binaries. >>> + http://msdn.microsoft.com/en-us/library/tawsa7cb.aspx >>> + Furthermore, according to RtlVirtualUnwind, the complete list of >>> + epilog marker is: >>> + - ret [c3] >>> + - ret n [c2 imm16] >>> + - rep ret [f3 c3] >>> + - jmp imm8 | imm32 [eb rel8] or [e9 rel32] >>> + - jmp qword ptr imm32 - not handled >>> + - rex jmp reg [4X ff eY] >>> + I would add: >>> + - pop reg [41 58-5f] or [58-5f] >> >> If you add "pop", and you'd add "add" and "lea" as well, >> right? It's not super clear what "marker" means, but all >> the instructions listed by RtlVirtualUnwind's docs are >> control flow instructions. And then, in the url you point >> above, we see: >> >> "These are the only legal forms for an epilog. It must consist of either >> an add RSP,constant or lea RSP,constant[FPReg], followed by a series >> of zero or more 8-byte register pops and a return or a jmp. (Only >> a subset of jmp statements are allowable in the epilog." >> >> So from both docs it seems to me that "marker" is always the >> last instruction of the epilogue, and that "pop" is not called >> a marker. > > This is in fact an optimization. If we found a pop, followed by > an epilog marker, there is not need to decode unwind info. I don't understand. pops will always be followed by a marker. How can that be an optimization? > >> Furthermore, >> >>> + >>> + We don't care about the instruction deallocating the frame: >>> + if it hasn't been executed, we can safely decode the insns; >>> + if it has been executed, the following epilog decoding will >>> + work. */ >>> + CORE_ADDR pc = cache->pc; >>> + CORE_ADDR cur_sp = cache->sp; >>> + struct gdbarch *gdbarch = get_frame_arch (this_frame); >>> + enum bfd_endian byte_order = gdbarch_byte_order (gdbarch); >>> + >>> + while (1) >>> + { >>> + gdb_byte op; >>> + gdb_byte rex; >>> + >>> + if (target_read_memory (pc, &op, 1) != 0) >>> + return -1; >>> + >>> + if (op == 0xc3) >>> + { >>> + /* Ret. */ >>> + cache->prev_rip_addr = cur_sp; >>> + cache->prev_sp = cur_sp + 8; >>> + return 1; >>> + } >>> + else if (op == 0xeb) >>> + { >>> + /* jmp rel8 */ >>> + gdb_byte rel8; >>> + >>> + if (target_read_memory (pc + 1, &rel8, 1) != 0) >>> + return -1; >>> + pc = pc + 2 + (signed char) rel8; >> >> this implementation follows jumps, and keeps looping >> at the jump destination. > > Right. > >> I see no hint that such thing >> as an epilogue with a jump is a valid epilogue, only that >> a jmp is only valid as replacement for ret. >> Can you show an example where following the jmp until >> you see a ret is necessary? > > Interesting remark. First attempt to answer is the case of a > jump to an epilogue. The jump to an epilogue would not be part of the epilogue. > But I may miss your point. My point is that the docs say the epilogue has this rigid format that always ends in a marker, and that a marker is a ret or a jmp (therefore calling "pop" a marker as in the "I would add" comment seems to me misleading). The code continues following the jmp, so it makes me believe the code is erroneously decoding something after the jmp that is not an epilogue (the caller or perhaps a tailcall). -- Pedro Alves