20000317 sourceware import
This commit is contained in:
126
libgloss/i386/Makefile.in
Normal file
126
libgloss/i386/Makefile.in
Normal file
@ -0,0 +1,126 @@
|
||||
# Copyright (c) 1997 Cygnus Support
|
||||
#
|
||||
# The authors hereby grant permission to use, copy, modify, distribute,
|
||||
# and license this software and its documentation for any purpose, provided
|
||||
# that existing copyright notices are retained in all copies and that this
|
||||
# notice is included verbatim in any distributions. No written agreement,
|
||||
# license, or royalty fee is required for any of the authorized uses.
|
||||
# Modifications to this software may be copyrighted by their authors
|
||||
# and need not follow the licensing terms described here, provided that
|
||||
# the new terms are clearly indicated on the first page of each file where
|
||||
# they apply.
|
||||
|
||||
VPATH = @srcdir@
|
||||
srcdir = @srcdir@
|
||||
objdir = .
|
||||
srcroot = $(srcdir)/../..
|
||||
objroot = $(objdir)/../..
|
||||
|
||||
prefix = @prefix@
|
||||
exec_prefix = @exec_prefix@
|
||||
|
||||
host_alias = @host_alias@
|
||||
target_alias = @target_alias@
|
||||
program_transform_name = @program_transform_name@
|
||||
|
||||
bindir = @bindir@
|
||||
libdir = @libdir@
|
||||
tooldir = $(exec_prefix)/$(target_alias)
|
||||
|
||||
# Multilib support variables.
|
||||
# TOP is used instead of MULTI{BUILD,SRC}TOP.
|
||||
MULTIDIRS =
|
||||
MULTISUBDIR =
|
||||
MULTIDO = true
|
||||
MULTICLEAN = true
|
||||
|
||||
INSTALL = @INSTALL@
|
||||
INSTALL_PROGRAM = @INSTALL_PROGRAM@
|
||||
INSTALL_DATA = @INSTALL_DATA@
|
||||
|
||||
SHELL = /bin/sh
|
||||
|
||||
CC = @CC@
|
||||
|
||||
#AS = @AS@
|
||||
AS = `if [ -f ${objroot}/../gas/as.new ] ; \
|
||||
then echo ${objroot}/../gas/as.new ; \
|
||||
else echo as ; fi`
|
||||
|
||||
AR = @AR@
|
||||
|
||||
#LD = @LD@
|
||||
LD = `if [ -f ${objroot}/../ld/ld.new ] ; \
|
||||
then echo ${objroot}/../ld/ld.new ; \
|
||||
else echo ld ; fi`
|
||||
|
||||
RANLIB = @RANLIB@
|
||||
|
||||
OBJDUMP = `if [ -f ${objroot}/../binutils/objdump ] ; \
|
||||
then echo ${objroot}/../binutils/objdump ; \
|
||||
else t='$(program_transform_name)'; echo objdump | sed -e $$t ; fi`
|
||||
OBJCOPY = `if [ -f ${objroot}/../binutils/objcopy ] ; \
|
||||
then echo ${objroot}/../binutils/objcopy ; \
|
||||
else t='$(program_transform_name)'; echo objcopy | sed -e $$t ; fi`
|
||||
|
||||
CRT0 = cygmon-crt0.o
|
||||
CYGMON_OBJS = cygmon-salib.o cygmon-gmon.o
|
||||
|
||||
CFLAGS = -g
|
||||
|
||||
GCC_LDFLAGS = `if [ -d ${objroot}/../gcc ] ; \
|
||||
then echo -L${objroot}/../gcc ; fi`
|
||||
|
||||
SCRIPTS = cygmon
|
||||
BSP = libcygmon.a
|
||||
|
||||
# Host specific makefile fragment comes in here.
|
||||
@host_makefile_frag@
|
||||
|
||||
all: ${CRT0} ${BSP}
|
||||
|
||||
#
|
||||
# here's where we build the board support packages for each target
|
||||
#
|
||||
libcygmon.a: $(CYGMON_OBJS)
|
||||
${AR} ${ARFLAGS} $@ $(CYGMON_OBJS)
|
||||
${RANLIB} $@
|
||||
|
||||
cygmon-salib.o: ${srcdir}/cygmon-salib.c
|
||||
$(CC) -c $(CFLAGS) @NEED_UNDERSCORE@ @IS_COFF@ $(<) -o $@
|
||||
|
||||
cygmon-crt0.o: ${srcdir}/cygmon-crt0.S
|
||||
$(CC) -c $(CFLAGS) @NEED_UNDERSCORE@ @IS_COFF@ $(<) -o $@
|
||||
|
||||
doc:
|
||||
|
||||
clean mostlyclean:
|
||||
rm -f a.out core *.i *~ *.o *-test *.srec *.dis *.map *.x
|
||||
|
||||
distclean maintainer-clean realclean: clean
|
||||
rm -f Makefile config.status a.out
|
||||
|
||||
.PHONY: install info install-info clean-info
|
||||
install:
|
||||
$(INSTALL_PROGRAM) $(CRT0) $(tooldir)/lib${MULTISUBDIR}/$(CRT0)
|
||||
@for bsp in ${BSP}; do\
|
||||
$(INSTALL_PROGRAM) $${bsp} $(tooldir)/lib${MULTISUBDIR}; \
|
||||
done
|
||||
@for script in ${SCRIPTS}; do\
|
||||
$(INSTALL_DATA) ${srcdir}/$${script}.ld $(tooldir)/lib${MULTISUBDIR}/$${script}.ld; \
|
||||
done
|
||||
|
||||
info:
|
||||
install-info:
|
||||
clean-info:
|
||||
|
||||
test.o: ${srcdir}/test.c
|
||||
|
||||
# these are for the BSPs
|
||||
${CRT0}: cygmon-crt0.S
|
||||
|
||||
Makefile: Makefile.in config.status @host_makefile_frag_path@
|
||||
$(SHELL) config.status
|
||||
|
||||
config.status: configure
|
||||
$(SHELL) config.status --recheck
|
1203
libgloss/i386/configure
vendored
Executable file
1203
libgloss/i386/configure
vendored
Executable file
File diff suppressed because it is too large
Load Diff
110
libgloss/i386/configure.in
Normal file
110
libgloss/i386/configure.in
Normal file
@ -0,0 +1,110 @@
|
||||
# Copyright (c) 1995, 1996 Cygnus Support
|
||||
#
|
||||
# The authors hereby grant permission to use, copy, modify, distribute,
|
||||
# and license this software and its documentation for any purpose, provided
|
||||
# that existing copyright notices are retained in all copies and that this
|
||||
# notice is included verbatim in any distributions. No written agreement,
|
||||
# license, or royalty fee is required for any of the authorized uses.
|
||||
# Modifications to this software may be copyrighted by their authors
|
||||
# and need not follow the licensing terms described here, provided that
|
||||
# the new terms are clearly indicated on the first page of each file where
|
||||
# they apply.
|
||||
#
|
||||
# Process this file with autoconf to produce a configure script.
|
||||
#
|
||||
AC_PREREQ(2.5)dnl
|
||||
AC_INIT(cygmon-salib.c)
|
||||
|
||||
if test "${enable_shared}" = "yes" ; then
|
||||
echo "Shared libraries not supported for cross compiling, ignored"
|
||||
fi
|
||||
|
||||
if test "$srcdir" = "." ; then
|
||||
if test "${with_target_subdir}" != "." ; then
|
||||
libgloss_topdir="${srcdir}/${with_multisrctop}../../.."
|
||||
else
|
||||
libgloss_topdir="${srcdir}/${with_multisrctop}../.."
|
||||
fi
|
||||
else
|
||||
libgloss_topdir="${srcdir}/../.."
|
||||
fi
|
||||
AC_CONFIG_AUX_DIR($libgloss_topdir)
|
||||
|
||||
AC_CANONICAL_SYSTEM
|
||||
AC_ARG_PROGRAM
|
||||
|
||||
AC_PROG_INSTALL
|
||||
|
||||
# FIXME: We temporarily define our own version of AC_PROG_CC. This is
|
||||
# copied from autoconf 2.12, but does not call AC_PROG_CC_WORKS. We
|
||||
# are building a library that must be included in all links, so we
|
||||
# can't link an executable until this lib is built.
|
||||
# autoconf should provide a way to do this.
|
||||
|
||||
AC_DEFUN(LIB_AC_PROG_CC,
|
||||
[AC_BEFORE([$0], [AC_PROG_CPP])dnl
|
||||
AC_CHECK_PROG(CC, gcc, gcc)
|
||||
if test -z "$CC"; then
|
||||
AC_CHECK_PROG(CC, cc, cc, , , /usr/ucb/cc)
|
||||
test -z "$CC" && AC_MSG_ERROR([no acceptable cc found in \$PATH])
|
||||
fi
|
||||
|
||||
AC_PROG_CC_GNU
|
||||
|
||||
if test $ac_cv_prog_gcc = yes; then
|
||||
GCC=yes
|
||||
dnl Check whether -g works, even if CFLAGS is set, in case the package
|
||||
dnl plays around with CFLAGS (such as to build both debugging and
|
||||
dnl normal versions of a library), tasteless as that idea is.
|
||||
ac_test_CFLAGS="${CFLAGS+set}"
|
||||
ac_save_CFLAGS="$CFLAGS"
|
||||
CFLAGS=
|
||||
AC_PROG_CC_G
|
||||
if test "$ac_test_CFLAGS" = set; then
|
||||
CFLAGS="$ac_save_CFLAGS"
|
||||
elif test $ac_cv_prog_cc_g = yes; then
|
||||
CFLAGS="-g -O2"
|
||||
else
|
||||
CFLAGS="-O2"
|
||||
fi
|
||||
else
|
||||
GCC=
|
||||
test "${CFLAGS+set}" = set || CFLAGS="-g"
|
||||
fi
|
||||
])
|
||||
|
||||
case "$target" in
|
||||
*coff)
|
||||
IS_COFF="-DCOFF"
|
||||
;;
|
||||
esac
|
||||
|
||||
LIB_AC_PROG_CC
|
||||
AS=${AS-as}
|
||||
AC_SUBST(AS)
|
||||
AR=${AR-ar}
|
||||
AC_SUBST(AR)
|
||||
LD=${LD-ld}
|
||||
AC_SUBST(LD)
|
||||
AC_SUBST(IS_COFF)
|
||||
AC_SUBST(NEED_UNDERSCORE)
|
||||
AC_PROG_RANLIB
|
||||
|
||||
host_makefile_frag=${srcdir}/../config/default.mh
|
||||
|
||||
dnl We have to assign the same value to other variables because autoconf
|
||||
dnl doesn't provide a mechanism to substitute a replacement keyword with
|
||||
dnl arbitrary data or pathnames.
|
||||
dnl
|
||||
host_makefile_frag_path=$host_makefile_frag
|
||||
AC_SUBST(host_makefile_frag_path)
|
||||
AC_SUBST_FILE(host_makefile_frag)
|
||||
|
||||
AC_OUTPUT(Makefile,
|
||||
. ${libgloss_topdir}/config-ml.in,
|
||||
srcdir=${srcdir}
|
||||
target=${target}
|
||||
ac_configure_args="${ac_configure_args} --enable-multilib"
|
||||
CONFIG_SHELL=${CONFIG_SHELL-/bin/sh}
|
||||
libgloss_topdir=${libgloss_topdir}
|
||||
)
|
82
libgloss/i386/cygmon-crt0.S
Normal file
82
libgloss/i386/cygmon-crt0.S
Normal file
@ -0,0 +1,82 @@
|
||||
/*
|
||||
* crt0 startup code for user programs running under Cygmon
|
||||
*
|
||||
* Copyright (c) 1998 Cygnus Support
|
||||
*
|
||||
* The authors hereby grant permission to use, copy, modify, distribute,
|
||||
* and license this software and its documentation for any purpose, provided
|
||||
* that existing copyright notices are retained in all copies and that this
|
||||
* notice is included verbatim in any distributions. No written agreement,
|
||||
* license, or royalty fee is required for any of the authorized uses.
|
||||
* Modifications to this software may be copyrighted by their authors
|
||||
* and need not follow the licensing terms described here, provided that
|
||||
* the new terms are clearly indicated on the first page of each file where
|
||||
* they apply.
|
||||
*/
|
||||
|
||||
#ifndef NEED_UNDERSCORE
|
||||
#define SYM(X) X
|
||||
#else
|
||||
#define SYM(X) _ ## X
|
||||
#endif
|
||||
|
||||
.data
|
||||
.align 8
|
||||
SYM(environ):
|
||||
.long 0
|
||||
|
||||
SYM(argc):
|
||||
.long 0
|
||||
|
||||
.text
|
||||
.align 4
|
||||
|
||||
.globl SYM(_start)
|
||||
SYM(_start):
|
||||
/* see if the stack is already setup. if not, then default
|
||||
* to using the value of %sp as set by the ROM monitor
|
||||
*/
|
||||
lea __stack,%eax
|
||||
cmpl $0,%eax
|
||||
jz 1f
|
||||
mov %eax, %esp
|
||||
1:
|
||||
mov $0, %ebp
|
||||
|
||||
lea __bss_start, %eax
|
||||
2:
|
||||
movb $0,(%eax)
|
||||
inc %eax
|
||||
cmp $__bss_end,%eax
|
||||
jl 2b
|
||||
|
||||
2:
|
||||
pushl $SYM(__sigtramp)
|
||||
pushl $0
|
||||
call SYM(__install_signal_handler)
|
||||
add $4, %esp
|
||||
|
||||
pushl $SYM(__do_global_dtors)
|
||||
call SYM(atexit)
|
||||
add $4, %esp
|
||||
|
||||
call SYM(__do_global_ctors)
|
||||
|
||||
pushl $SYM(argc)
|
||||
call SYM(__get_program_arguments)
|
||||
add $4, %esp
|
||||
|
||||
pushl %eax
|
||||
lea SYM(argc), %ebx
|
||||
pushl (%ebx)
|
||||
call SYM(main)
|
||||
add $8, %esp
|
||||
|
||||
/* call exit from the C library so atexit gets called, and the
|
||||
* C++ destructors get run. This calls our exit routine below
|
||||
* when it's done.
|
||||
*/
|
||||
pushl %eax
|
||||
call SYM(exit)
|
||||
3:
|
||||
jmp 3b
|
362
libgloss/i386/cygmon-gmon.c
Normal file
362
libgloss/i386/cygmon-gmon.c
Normal file
@ -0,0 +1,362 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* 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.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``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 REGENTS OR CONTRIBUTORS 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.
|
||||
*/
|
||||
|
||||
/*
|
||||
* This is a modified gmon.c by J.W.Hawtin <oolon@ankh.org>,
|
||||
* 14/8/96 based on the original gmon.c in GCC and the hacked version
|
||||
* solaris 2 sparc version (config/sparc/gmon-sol.c) by Mark Eichin. To do
|
||||
* process profiling on solaris 2.X X86
|
||||
*
|
||||
* It must be used in conjunction with sol2-gc1.asm, which is used to start
|
||||
* and stop process monitoring.
|
||||
*
|
||||
* Differences.
|
||||
*
|
||||
* On Solaris 2 _mcount is called by library functions not mcount, so support
|
||||
* has been added for both.
|
||||
*
|
||||
* Also the prototype for profil() is different
|
||||
*
|
||||
* Solaris 2 does not seem to have char *minbrk which allows the setting of
|
||||
* the minimum SBRK region so this code has been removed and lets pray malloc
|
||||
* does not mess it up.
|
||||
*
|
||||
* Notes
|
||||
*
|
||||
* This code could easily be integrated with the original gmon.c and perhaps
|
||||
* should be.
|
||||
*/
|
||||
|
||||
#ifndef lint
|
||||
static char sccsid[] = "@(#)gmon.c 5.3 (Berkeley) 5/22/91";
|
||||
#endif /* not lint */
|
||||
|
||||
#define DEBUG
|
||||
#ifdef DEBUG
|
||||
#include <stdio.h>
|
||||
#endif
|
||||
|
||||
#include "cygmon-gmon.h"
|
||||
|
||||
/*
|
||||
* froms is actually a bunch of unsigned shorts indexing tos
|
||||
*/
|
||||
static int profiling = 3;
|
||||
static unsigned short *froms;
|
||||
static struct tostruct *tos = 0;
|
||||
static long tolimit = 0;
|
||||
static char *s_lowpc = 0;
|
||||
static char *s_highpc = 0;
|
||||
static unsigned long s_textsize = 0;
|
||||
|
||||
static int ssiz;
|
||||
static char *sbuf;
|
||||
static int s_scale;
|
||||
/* see profil(2) where this is describe (incorrectly) */
|
||||
#define SCALE_1_TO_1 0x10000L
|
||||
|
||||
#define MSG "No space for profiling buffer(s)\n"
|
||||
|
||||
extern int errno;
|
||||
|
||||
int
|
||||
monstartup(lowpc, highpc)
|
||||
char *lowpc;
|
||||
char *highpc;
|
||||
{
|
||||
int monsize;
|
||||
char *buffer;
|
||||
register int o;
|
||||
|
||||
/*
|
||||
* round lowpc and highpc to multiples of the density we're using
|
||||
* so the rest of the scaling (here and in gprof) stays in ints.
|
||||
*/
|
||||
lowpc = (char *)
|
||||
ROUNDDOWN((unsigned)lowpc, HISTFRACTION*sizeof(HISTCOUNTER));
|
||||
s_lowpc = lowpc;
|
||||
highpc = (char *)
|
||||
ROUNDUP((unsigned)highpc, HISTFRACTION*sizeof(HISTCOUNTER));
|
||||
s_highpc = highpc;
|
||||
s_textsize = highpc - lowpc;
|
||||
monsize = (s_textsize / HISTFRACTION) + sizeof(struct phdr);
|
||||
buffer = (char *) sbrk (monsize);
|
||||
if (buffer == (char *) -1)
|
||||
{
|
||||
write (2, MSG , sizeof(MSG));
|
||||
return;
|
||||
}
|
||||
bzero (buffer, monsize);
|
||||
froms = (unsigned short *) sbrk (s_textsize / HASHFRACTION);
|
||||
if (froms == (unsigned short *) -1)
|
||||
{
|
||||
write(2, MSG, sizeof(MSG));
|
||||
froms = 0;
|
||||
return;
|
||||
}
|
||||
bzero (froms, s_textsize / HASHFRACTION);
|
||||
tolimit = s_textsize * ARCDENSITY / 100;
|
||||
if (tolimit < MINARCS)
|
||||
{
|
||||
tolimit = MINARCS;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (tolimit > 65534)
|
||||
{
|
||||
tolimit = 65534;
|
||||
}
|
||||
}
|
||||
tos = (struct tostruct *) sbrk( tolimit * sizeof( struct tostruct ) );
|
||||
if (tos == (struct tostruct *) -1)
|
||||
{
|
||||
write (2, MSG, sizeof(MSG));
|
||||
froms = 0;
|
||||
tos = 0;
|
||||
return;
|
||||
}
|
||||
bzero (tos, tolimit * sizeof( struct tostruct ) );
|
||||
tos[0].link = 0;
|
||||
sbuf = buffer;
|
||||
ssiz = monsize;
|
||||
( (struct phdr *) buffer ) -> lpc = lowpc;
|
||||
( (struct phdr *) buffer ) -> hpc = highpc;
|
||||
( (struct phdr *) buffer ) -> ncnt = ssiz;
|
||||
monsize -= sizeof(struct phdr);
|
||||
if ( monsize <= 0 )
|
||||
return;
|
||||
o = highpc - lowpc;
|
||||
if (monsize < o)
|
||||
{
|
||||
s_scale = ( (float) monsize / o ) * SCALE_1_TO_1;
|
||||
}
|
||||
else
|
||||
s_scale = SCALE_1_TO_1;
|
||||
moncontrol (1);
|
||||
}
|
||||
|
||||
void
|
||||
_mcleanup()
|
||||
{
|
||||
int fd;
|
||||
int fromindex;
|
||||
int endfrom;
|
||||
char *frompc;
|
||||
int toindex;
|
||||
struct rawarc rawarc;
|
||||
|
||||
moncontrol (0);
|
||||
profil_write (1, sbuf, ssiz);
|
||||
|
||||
endfrom = s_textsize / (HASHFRACTION * sizeof(*froms));
|
||||
for ( fromindex = 0 ; fromindex < endfrom ; fromindex++ )
|
||||
{
|
||||
if ( froms[fromindex] == 0 )
|
||||
{
|
||||
continue;
|
||||
}
|
||||
frompc = s_lowpc + (fromindex * HASHFRACTION * sizeof(*froms));
|
||||
for (toindex=froms[fromindex]; toindex!=0; toindex=tos[toindex].link)
|
||||
{
|
||||
rawarc.raw_frompc = (unsigned long) frompc;
|
||||
rawarc.raw_selfpc = (unsigned long) tos[toindex].selfpc;
|
||||
rawarc.raw_count = tos[toindex].count;
|
||||
profil_write (2, &rawarc, sizeof (rawarc));
|
||||
}
|
||||
}
|
||||
profil_write (3, 0, 0);
|
||||
}
|
||||
|
||||
static char already_setup = 0;
|
||||
|
||||
_mcount()
|
||||
{
|
||||
register char *selfpc;
|
||||
register unsigned short *frompcindex;
|
||||
register struct tostruct *top;
|
||||
register struct tostruct *prevtop;
|
||||
register long toindex;
|
||||
|
||||
/*
|
||||
* find the return address for mcount,
|
||||
* and the return address for mcount's caller.
|
||||
*/
|
||||
|
||||
/* selfpc = pc pushed by mcount call.
|
||||
This identifies the function that was just entered. */
|
||||
selfpc = (void *) __builtin_return_address (0);
|
||||
/* frompcindex = pc in preceding frame.
|
||||
This identifies the caller of the function just entered. */
|
||||
frompcindex = (void *) __builtin_return_address (1);
|
||||
|
||||
if (! already_setup)
|
||||
{
|
||||
extern etext();
|
||||
extern _ftext();
|
||||
already_setup = 1;
|
||||
monstartup(_ftext, etext);
|
||||
atexit(_mcleanup);
|
||||
}
|
||||
/*
|
||||
* check that we are profiling
|
||||
* and that we aren't recursively invoked.
|
||||
*/
|
||||
if (profiling)
|
||||
{
|
||||
goto out;
|
||||
}
|
||||
profiling++;
|
||||
/*
|
||||
* check that frompcindex is a reasonable pc value.
|
||||
* for example: signal catchers get called from the stack,
|
||||
* not from text space. too bad.
|
||||
*/
|
||||
frompcindex = (unsigned short *)((long)frompcindex - (long)s_lowpc);
|
||||
if ((unsigned long)frompcindex > s_textsize)
|
||||
{
|
||||
goto done;
|
||||
}
|
||||
frompcindex =
|
||||
&froms[((long)frompcindex) / (HASHFRACTION * sizeof(*froms))];
|
||||
toindex = *frompcindex;
|
||||
if (toindex == 0)
|
||||
{
|
||||
/*
|
||||
* first time traversing this arc
|
||||
*/
|
||||
toindex = ++tos[0].link;
|
||||
if (toindex >= tolimit)
|
||||
{
|
||||
goto overflow;
|
||||
}
|
||||
*frompcindex = toindex;
|
||||
top = &tos[toindex];
|
||||
top->selfpc = selfpc;
|
||||
top->count = 1;
|
||||
top->link = 0;
|
||||
goto done;
|
||||
}
|
||||
top = &tos[toindex];
|
||||
if (top->selfpc == selfpc)
|
||||
{
|
||||
/*
|
||||
* arc at front of chain; usual case.
|
||||
*/
|
||||
top->count++;
|
||||
goto done;
|
||||
}
|
||||
/*
|
||||
* have to go looking down chain for it.
|
||||
* top points to what we are looking at,
|
||||
* prevtop points to previous top.
|
||||
* we know it is not at the head of the chain.
|
||||
*/
|
||||
for (; /* goto done */; )
|
||||
{
|
||||
if (top->link == 0)
|
||||
{
|
||||
/*
|
||||
* top is end of the chain and none of the chain
|
||||
* had top->selfpc == selfpc.
|
||||
* so we allocate a new tostruct
|
||||
* and link it to the head of the chain.
|
||||
*/
|
||||
toindex = ++tos[0].link;
|
||||
if (toindex >= tolimit)
|
||||
{
|
||||
goto overflow;
|
||||
}
|
||||
top = &tos[toindex];
|
||||
top->selfpc = selfpc;
|
||||
top->count = 1;
|
||||
top->link = *frompcindex;
|
||||
*frompcindex = toindex;
|
||||
goto done;
|
||||
}
|
||||
/*
|
||||
* otherwise, check the next arc on the chain.
|
||||
*/
|
||||
prevtop = top;
|
||||
top = &tos[top->link];
|
||||
if (top->selfpc == selfpc)
|
||||
{
|
||||
/*
|
||||
* there it is.
|
||||
* increment its count
|
||||
* move it to the head of the chain.
|
||||
*/
|
||||
top->count++;
|
||||
toindex = prevtop->link;
|
||||
prevtop->link = top->link;
|
||||
top->link = *frompcindex;
|
||||
*frompcindex = toindex;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
done:
|
||||
profiling--;
|
||||
/* and fall through */
|
||||
out:
|
||||
return; /* normal return restores saved registers */
|
||||
|
||||
overflow:
|
||||
profiling++; /* halt further profiling */
|
||||
# define TOLIMIT "mcount: tos overflow\n"
|
||||
write (2, TOLIMIT, sizeof(TOLIMIT));
|
||||
goto out;
|
||||
}
|
||||
|
||||
/*
|
||||
* Control profiling
|
||||
* profiling is what mcount checks to see if
|
||||
* all the data structures are ready.
|
||||
*/
|
||||
moncontrol(mode)
|
||||
int mode;
|
||||
{
|
||||
if (mode)
|
||||
{
|
||||
/* start */
|
||||
profil((unsigned short *)(sbuf + sizeof(struct phdr)),
|
||||
ssiz - sizeof(struct phdr),
|
||||
(int)s_lowpc, s_scale);
|
||||
|
||||
profiling = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* stop */
|
||||
profil((unsigned short *)0, 0, 0, 0);
|
||||
profiling = 3;
|
||||
}
|
||||
}
|
35
libgloss/i386/cygmon-gmon.h
Normal file
35
libgloss/i386/cygmon-gmon.h
Normal file
@ -0,0 +1,35 @@
|
||||
#ifndef GMON_CYGMON_H
|
||||
#define GMON_CYGMON_H
|
||||
|
||||
struct phdr
|
||||
{
|
||||
char *lpc;
|
||||
char *hpc;
|
||||
int ncnt;
|
||||
};
|
||||
|
||||
|
||||
#define HISTFRACTION 2
|
||||
#define HISTCOUNTER unsigned short
|
||||
#define HASHFRACTION 1
|
||||
#define ARCDENSITY 2
|
||||
#define MINARCS 50
|
||||
|
||||
struct tostruct
|
||||
{
|
||||
char *selfpc;
|
||||
long count;
|
||||
unsigned short link;
|
||||
};
|
||||
|
||||
struct rawarc
|
||||
{
|
||||
unsigned long raw_frompc;
|
||||
unsigned long raw_selfpc;
|
||||
long raw_count;
|
||||
};
|
||||
|
||||
#define ROUNDDOWN(x,y) (((x)/(y))*(y))
|
||||
#define ROUNDUP(x,y) ((((x)+(y)-1)/(y))*(y))
|
||||
|
||||
#endif
|
165
libgloss/i386/cygmon-salib.c
Normal file
165
libgloss/i386/cygmon-salib.c
Normal file
@ -0,0 +1,165 @@
|
||||
/*
|
||||
* Standard x86 syscalls for user programs running under Cygmon
|
||||
*
|
||||
* Copyright (c) 1998 Cygnus Support
|
||||
*
|
||||
* The authors hereby grant permission to use, copy, modify, distribute,
|
||||
* and license this software and its documentation for any purpose, provided
|
||||
* that existing copyright notices are retained in all copies and that this
|
||||
* notice is included verbatim in any distributions. No written agreement,
|
||||
* license, or royalty fee is required for any of the authorized uses.
|
||||
* Modifications to this software may be copyrighted by their authors
|
||||
* and need not follow the licensing terms described here, provided that
|
||||
* the new terms are clearly indicated on the first page of each file where
|
||||
* they apply.
|
||||
*/
|
||||
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
#include "cygmon-syscall.h"
|
||||
#include <sys/time.h>
|
||||
|
||||
extern int errno;
|
||||
|
||||
_syscall3(int,write,int,i,char *,c,int,len);
|
||||
|
||||
_syscall3(int,read,int,i,char *,c,int,len);
|
||||
|
||||
_syscall2(int,kill,int,pid,int,signal);
|
||||
|
||||
_syscall2(void,__install_signal_handler,int,arg,void *,handler);
|
||||
_syscall1(char **,__get_program_arguments,int *,argc);
|
||||
|
||||
_syscall1(void,__sys_exit,int,exitcode);
|
||||
_syscall1(void,putTtyChar,int,character);
|
||||
_syscall1(time_t,time,time_t *,ptr);
|
||||
_syscall2(int, gettimeofday, struct timeval *,time, struct timezone *,z);
|
||||
_syscall3(int, __open, const char *, filename, int, mode, int, filemode);
|
||||
_syscall4(void, profil, unsigned short *, buff, unsigned int, bufsiz,
|
||||
unsigned int, offset, unsigned int, scale);
|
||||
_syscall1(int, close, int, fd);
|
||||
|
||||
/* Bleah. */
|
||||
int
|
||||
open (const char *filename, int mode, ...)
|
||||
{
|
||||
return __open (filename, mode, 0644);
|
||||
}
|
||||
|
||||
/* Ultra-super cheezy. */
|
||||
int
|
||||
isatty (int i)
|
||||
{
|
||||
return i<3;
|
||||
}
|
||||
|
||||
char *
|
||||
sbrk (int amt)
|
||||
{
|
||||
extern char _end;
|
||||
static char *ptr = 0;
|
||||
char *res;
|
||||
if (ptr == 0)
|
||||
ptr = &_end;
|
||||
if (amt == 0)
|
||||
return (char *)ptr;
|
||||
|
||||
if (((long)ptr) % 8)
|
||||
ptr = ptr + (8 - (((long)(ptr)) % 8));
|
||||
res = ptr;
|
||||
ptr += amt;
|
||||
return (char *)res;
|
||||
}
|
||||
|
||||
void
|
||||
_exit(int i)
|
||||
{
|
||||
while(1) {
|
||||
__sys_exit (i);
|
||||
asm(" int $3");
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
fstat(int des, struct stat *buf)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
int
|
||||
lseek(int des,unsigned long offset, int whence)
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
int
|
||||
getpid ()
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Simple replacement for the clock() syscall. */
|
||||
clock_t
|
||||
clock ()
|
||||
{
|
||||
struct timeval t;
|
||||
|
||||
gettimeofday (&t, 0);
|
||||
return t.tv_sec * 1000 + (t.tv_usec / 1000);
|
||||
}
|
||||
|
||||
#ifndef COFF
|
||||
typedef void (*ctp)();
|
||||
void
|
||||
__do_global_ctors ()
|
||||
{
|
||||
extern int __CTOR_LIST__;
|
||||
int *c = &__CTOR_LIST__;
|
||||
c++;
|
||||
while (*c)
|
||||
{
|
||||
ctp d = (ctp)*c;
|
||||
(d)();
|
||||
c++;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
__do_global_dtors ()
|
||||
{
|
||||
extern int __DTOR_LIST__;
|
||||
int *c = &__DTOR_LIST__;
|
||||
int *cp = c;
|
||||
c++;
|
||||
while (*c)
|
||||
{
|
||||
c++;
|
||||
}
|
||||
c--;
|
||||
while (c > cp)
|
||||
{
|
||||
ctp d = (ctp)*c;
|
||||
(*d)();
|
||||
c--;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
void
|
||||
profil_write (int type, char *buffer, int len)
|
||||
{
|
||||
static int des = -1;
|
||||
|
||||
if (des < 0)
|
||||
{
|
||||
des = open ("gmon.out", O_WRONLY | O_CREAT | O_TRUNC, 0644);
|
||||
}
|
||||
if (len == 0)
|
||||
{
|
||||
close (des);
|
||||
}
|
||||
else
|
||||
{
|
||||
write (des, buffer, len);
|
||||
}
|
||||
}
|
96
libgloss/i386/cygmon-syscall.h
Normal file
96
libgloss/i386/cygmon-syscall.h
Normal file
@ -0,0 +1,96 @@
|
||||
/*
|
||||
* Standard x86 syscalls for user programs running under Cygmon
|
||||
*
|
||||
* Copyright (c) 1998 Cygnus Support
|
||||
*
|
||||
* The authors hereby grant permission to use, copy, modify, distribute,
|
||||
* and license this software and its documentation for any purpose, provided
|
||||
* that existing copyright notices are retained in all copies and that this
|
||||
* notice is included verbatim in any distributions. No written agreement,
|
||||
* license, or royalty fee is required for any of the authorized uses.
|
||||
* Modifications to this software may be copyrighted by their authors
|
||||
* and need not follow the licensing terms described here, provided that
|
||||
* the new terms are clearly indicated on the first page of each file where
|
||||
* they apply.
|
||||
*/
|
||||
|
||||
#ifndef CYGMON_SYSCALL_H
|
||||
#define CYGMON_SYSCALL_H
|
||||
|
||||
#define __MAX_ERRNO 4096
|
||||
|
||||
#define _syscall0(type,name) \
|
||||
type name(void) \
|
||||
{ \
|
||||
long __res; \
|
||||
__asm__ __volatile__ ("int $0x80" \
|
||||
: "=a" (__res) \
|
||||
: "0" (SYS_##name)); \
|
||||
return (type) __res; \
|
||||
}
|
||||
|
||||
#define _syscall1(type,name,atype,a) \
|
||||
type name(atype a) \
|
||||
{ \
|
||||
long __res, dummy; \
|
||||
__asm__ __volatile__ ("int $0x80" \
|
||||
: "=a" (__res), "=&b" (dummy) \
|
||||
: "0" (SYS_##name),"1" ((long)(a))); \
|
||||
return (type) __res; \
|
||||
}
|
||||
|
||||
#define _syscall2(type,name,atype,a,btype,b) \
|
||||
type name(atype a,btype b) \
|
||||
{ \
|
||||
long __res, dummy; \
|
||||
__asm__ __volatile__ ("int $0x80" \
|
||||
: "=a" (__res), "=&b" (dummy) \
|
||||
: "0" (SYS_##name),"1" ((long)(a)),"c" ((long)(b))); \
|
||||
return (type) __res; \
|
||||
}
|
||||
|
||||
#define _syscall3(type,name,atype,a,btype,b,ctype,c) \
|
||||
type name(atype a,btype b,ctype c) \
|
||||
{ \
|
||||
long __res, dummy; \
|
||||
__asm__ __volatile__ ("int $0x80" \
|
||||
: "=a" (__res), "=&b" (dummy) \
|
||||
: "0" (SYS_##name),"1" ((long)(a)),"c" ((long)(b)),"d" ((long)(c))); \
|
||||
return (type) __res; \
|
||||
}
|
||||
|
||||
#define _syscall4(type,name,atype,a,btype,b,ctype,c,dtype,d) \
|
||||
type name (atype a, btype b, ctype c, dtype d) \
|
||||
{ \
|
||||
long __res; \
|
||||
__asm__ __volatile__ ("int $0x80" \
|
||||
: "=a" (__res) \
|
||||
: "0" (SYS_##name),"b" ((long)(a)),"c" ((long)(b)), \
|
||||
"d" ((long)(c)),"S" ((long)(d))); \
|
||||
return (type) __res; \
|
||||
}
|
||||
|
||||
#define _syscall5(type,name,atype,a,btype,b,ctype,c,dtype,d,etype,e) \
|
||||
type name (atype a,btype b,ctype c,dtype d,etype e) \
|
||||
{ \
|
||||
long __res; \
|
||||
__asm__ __volatile__ ("int $0x80" \
|
||||
: "=a" (__res) \
|
||||
: "0" (SYS_##name),"b" ((long)(a)),"c" ((long)(b)), \
|
||||
"d" ((long)(c)),"S" ((long)(d)),"D" ((long)(e))); \
|
||||
return (type) __res; \
|
||||
}
|
||||
|
||||
#define SYS_putTtyChar 2
|
||||
#define SYS___sys_exit 1
|
||||
#define SYS_read 3
|
||||
#define SYS_write 4
|
||||
#define SYS___open 5
|
||||
#define SYS_close 6
|
||||
#define SYS_kill 37
|
||||
#define SYS_time 13
|
||||
#define SYS_gettimeofday 156
|
||||
#define SYS___install_signal_handler 48
|
||||
#define SYS_profil 98
|
||||
#define SYS___get_program_arguments 184
|
||||
#endif /* SYSCALL_H */
|
88
libgloss/i386/cygmon.ld
Normal file
88
libgloss/i386/cygmon.ld
Normal file
@ -0,0 +1,88 @@
|
||||
STARTUP(cygmon-crt0.o)
|
||||
ENTRY(_start)
|
||||
GROUP(-lcygmon -lc -lcygmon -lgcc)
|
||||
SEARCH_DIR(.)
|
||||
__DYNAMIC = 0;
|
||||
|
||||
/*
|
||||
* Allocate the stack to be at the top of memory, since the stack
|
||||
* grows down
|
||||
*/
|
||||
PROVIDE (__stack = 0x500000);
|
||||
|
||||
/*
|
||||
* Initalize some symbols to be zero so we can reference them in the
|
||||
* crt0 without core dumping. These functions are all optional, but
|
||||
* we do this so we can have our crt0 always use them if they exist.
|
||||
* This is so BSPs work better when using the crt0 installed with gcc.
|
||||
* We have to initalize them twice, so we multiple object file
|
||||
* formats, as some prepend an underscore.
|
||||
*/
|
||||
PROVIDE (hardware_init_hook = 0);
|
||||
PROVIDE (software_init_hook = 0);
|
||||
PROVIDE (__mem_start = 0x100000);
|
||||
PROVIDE (___mem_start = 0x100000);
|
||||
SECTIONS
|
||||
{
|
||||
. = 0x100000;
|
||||
.text : {
|
||||
_ftext = . ;
|
||||
*(.init)
|
||||
eprol = .;
|
||||
*(.text)
|
||||
PROVIDE (__runtime_reloc_start = .);
|
||||
*(.rel.sdata)
|
||||
PROVIDE (__runtime_reloc_stop = .);
|
||||
*(.fini)
|
||||
__CTOR_LIST__ = .;
|
||||
CONSTRUCTORS
|
||||
LONG(-1)
|
||||
*(.ctors)
|
||||
LONG(0)
|
||||
__CTOR_END__ = .;
|
||||
__DTOR_LIST__ = .;
|
||||
LONG(-1)
|
||||
*(.dtors)
|
||||
LONG(0)
|
||||
__DTOR_END__ = .;
|
||||
etext = .;
|
||||
_etext = .;
|
||||
}
|
||||
. = .;
|
||||
.rdata : {
|
||||
*(.rdata)
|
||||
}
|
||||
_fdata = ALIGN(16);
|
||||
.data : {
|
||||
*(.data)
|
||||
}
|
||||
. = ALIGN(8);
|
||||
_gp = . + 0x8000;
|
||||
__global = . + 0x8000;
|
||||
.lit8 : {
|
||||
*(.lit8)
|
||||
}
|
||||
.lit4 : {
|
||||
*(.lit4)
|
||||
}
|
||||
.sdata : {
|
||||
*(.sdata)
|
||||
}
|
||||
. = ALIGN(4);
|
||||
edata = .;
|
||||
_edata = .;
|
||||
fbss = .;
|
||||
_fbss = .;
|
||||
.sbss : {
|
||||
*(.sbss)
|
||||
*(.scommon)
|
||||
}
|
||||
.bss : {
|
||||
__bss_start = . ;
|
||||
*(.bss)
|
||||
*(COMMON)
|
||||
__bss_end = . ;
|
||||
}
|
||||
end = .;
|
||||
_end = .;
|
||||
}
|
Reference in New Issue
Block a user