calls.c revision 7c478bd95313f5f23a4c958a745db2134aa03244
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License, Version 1.0 only
* (the "License"). You may not use this file except in compliance
* with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright 2004 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
#pragma ident "%Z%%M% %I% %E% SMI"
#include "gprof.h"
/*
* a namelist entry to be the child of indirect calls
*/
nltype indirectchild = {
"(*)", /* the name */
&modules, /* module [-c only for prog txtspace] */
(pctype)0, /* the pc entry point */
(pctype)0, /* aligned entry point */
(unsigned long)0, /* function size */
(unsigned char)0, /* symbol information */
(size_t)0, /* ticks in this routine */
(double)0.0, /* ticks in this routine (as double) */
(double)0.0, /* cumulative ticks in children */
(long)0, /* how many times called */
(long)0, /* how many calls to self */
(double)1.0, /* propagation fraction */
(double)0.0, /* self propagation time */
(double)0.0, /* child propagation time */
(bool)0, /* print flag */
(int)0, /* index in the graph list */
(int)0, /* graph call chain top-sort order */
(int)0, /* internal number of cycle on */
(struct nl *)0, /* pointer to next member of cycle */
(arctype *)0, /* list of caller arcs */
(arctype *)0, /* list of callee arcs */
(unsigned long)0 /* number of callers */
};
void
{
unsigned long instructp;
if (textspace == 0) {
return;
}
return;
return;
#ifdef DEBUG
if (debug & CALLSDEBUG) {
printf("[findcalls] %s: 0x%llx to 0x%llx\n",
}
#endif /* DEBUG */
length = 4;
case CALL:
/*
* May be a call, better check it out.
*/
#ifdef DEBUG
if (debug & CALLSDEBUG) {
printf("[findcalls]\t0x%x:call\n",
}
#endif /* DEBUG */
break;
case FMT3_0x10:
continue;
#ifdef DEBUG
if (debug & CALLSDEBUG)
printf("[findcalls]\t0x%x:jmpl",
#endif /* DEBUG */
#ifdef DEBUG
if (debug & CALLSDEBUG) {
case R_O7:
printf("\tprobably a RETL\n");
break;
case R_I7:
printf("\tprobably a RET\n");
break;
default:
printf(", but not a call: "
"linked to g0\n");
}
}
#endif /* DEBUG */
continue;
}
#ifdef DEBUG
if (debug & CALLSDEBUG) {
printf("\toperands are DST = R%d,\tSRC = R%d",
}
#endif /* DEBUG */
#ifdef DEBUG
if (debug & CALLSDEBUG) {
printf(" - 0x%x\n",
} else {
printf(" + 0x%x\n",
}
}
#endif /* DEBUG */
case R_G0:
/*
* absolute address, simm 13
*/
break;
default:
/*
* indirect call
*/
continue;
}
} else {
/*
* two register sources, all cases are indirect
*/
#ifdef DEBUG
if (debug & CALLSDEBUG) {
}
#endif /* DEBUG */
continue;
}
break;
default:
continue;
}
/*
* Check that the destination is the address of
* a function; this allows us to differentiate
* real calls from someone trying to get the PC,
* e.g. position independent switches.
*/
#ifdef DEBUG
if (debug & CALLSDEBUG) {
printf(" childp->value 0x%llx\n",
}
#endif /* DEBUG */
/*
* a hit
*/
continue;
}
}
/*
* else:
* it looked like a call,
* but it wasn't to anywhere.
*/
#ifdef DEBUG
if (debug & CALLSDEBUG) {
printf("[findcalls]\tbut it's a switch or a botch\n");
}
#endif /* DEBUG */
continue;
}
}