From owner-p4-projects Sat Apr 6 12:24:56 2002 Delivered-To: p4-projects@freebsd.org Received: by hub.freebsd.org (Postfix, from userid 32767) id DC8EE37B416; Sat, 6 Apr 2002 12:24:42 -0800 (PST) Delivered-To: perforce@freebsd.org Received: from freefall.freebsd.org (freefall.FreeBSD.org [216.136.204.21]) by hub.freebsd.org (Postfix) with ESMTP id 316FA37B421 for ; Sat, 6 Apr 2002 12:24:39 -0800 (PST) Received: (from perforce@localhost) by freefall.freebsd.org (8.11.6/8.11.6) id g36KOcF64675 for perforce@freebsd.org; Sat, 6 Apr 2002 12:24:38 -0800 (PST) (envelope-from marcel@freebsd.org) Date: Sat, 6 Apr 2002 12:24:38 -0800 (PST) Message-Id: <200204062024.g36KOcF64675@freefall.freebsd.org> X-Authentication-Warning: freefall.freebsd.org: perforce set sender to marcel@freebsd.org using -f From: Marcel Moolenaar Subject: PERFORCE change 9226 for review To: Perforce Change Reviews Sender: owner-p4-projects@FreeBSD.ORG Precedence: bulk List-ID: List-Archive: (Web Archive) List-Help: (List Instructions) List-Subscribe: List-Unsubscribe: X-Loop: FreeBSD.ORG http://people.freebsd.org/~peter/p4db/chv.cgi?CH=9226 Change 9226 by marcel@marcel_vaio on 2002/04/06 12:24:33 Implement _Unwind_FindTableEntry(). Enable sanity checking for now to make sure we got it right. Affected files ... ... //depot/projects/ia64/lib/libc/ia64/gen/unwind.c#2 edit Differences ... ==== //depot/projects/ia64/lib/libc/ia64/gen/unwind.c#2 (text+ko) ==== @@ -1,6 +1,124 @@ -/* Provide no unwind info to g++, let it use the fallbacks */ -void * -_Unwind_FindTableEntry(void) +/* + * Copyright (c) 2002 Marcel Moolenaar + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + * $FreeBSD$ + */ + +#include + +#include +#include +#include + +#include + +#ifndef PT_IA_64_UNWIND +#define PT_IA_64_UNWIND 0x70000001 +#endif + +#define SANITY 1 + +struct ia64_unwind_entry +{ + Elf64_Addr start; + Elf64_Addr end; + Elf64_Addr descr; +}; + +struct ia64_unwind_entry * +_Unwind_FindTableEntry(const void *pc, unsigned long *pseg, unsigned long *pgp) { - return (void *)0; + Dl_info info; + Elf_Dyn *dyn; + Elf_Ehdr *ehdr; + Elf_Phdr *phdr; + char *p, *p_top; + struct ia64_unwind_entry *unw, *res; + register unsigned long gp __asm__("gp"); /* XXX assumes gcc */ + size_t l, m, r; + + if (!dladdr(pc, &info)) + return NULL; + + ehdr = (Elf_Ehdr*)info.dli_fbase; + +#if SANITY + assert(IS_ELF(*ehdr)); + assert(ehdr->e_ident[EI_CLASS] == ELFCLASS64); + assert(ehdr->e_ident[EI_DATA] == ELFDATA2LSB); + assert(ehdr->e_machine == EM_IA_64); +#endif + + *pgp = gp; + *pseg = 0UL; + res = NULL; + + p = (char*)info.dli_fbase + ehdr->e_phoff; + p_top = p + ehdr->e_phnum * ehdr->e_phentsize; + while (p < p_top) { + phdr = (Elf_Phdr*)p; + + switch (phdr->p_type) { + case PT_DYNAMIC: + dyn = (Elf_Dyn*)phdr->p_vaddr; + while (dyn->d_tag != DT_NULL) { + if (dyn->d_tag == DT_PLTGOT) { + *pgp = dyn->d_un.d_ptr; + break; + } + dyn++; + } + break; + case PT_LOAD: + if (pc >= (void*)phdr->p_vaddr && + pc < (void*)(phdr->p_vaddr + phdr->p_memsz)) + *pseg = phdr->p_vaddr; + break; + case PT_IA_64_UNWIND: +#if SANITY + assert(*pseg != 0UL); + assert(res == NULL); +#endif + unw = (struct ia64_unwind_entry*)phdr->p_vaddr; + l = 0; + r = phdr->p_memsz / sizeof(struct ia64_unwind_entry); + while (l < r) { + m = (l + r) >> 1; + res = unw + m; + if (pc < (void*)(res->start + *pseg)) + r = m; + else if (pc >= (void*)(res->end + *pseg)) + l = m + 1; + else + break; /* found */ + } + break; + } + + p += ehdr->e_phentsize; + } + + return res; } To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe p4-projects" in the body of the message