Landing fix for bug 388564. Adding Dtrace probes to the JS engine. Patch by padraig.obriain@sun.com and brendan@sun.com, and some intergration work done by jst@mozilla.org. r=brendan@mozilla.org, igor@mir2.org, sayrer@gmail.com, and r+a=ted.mielczarek@gmail.com.

This commit is contained in:
jst%mozilla.org 2007-10-19 22:24:32 +00:00
Родитель 781819308e
Коммит 68fa078d79
7 изменённых файлов: 596 добавлений и 11 удалений

Просмотреть файл

@ -1048,6 +1048,15 @@ ifdef NO_LD_ARCHIVE_FLAGS
SUB_SHLOBJS = $(SUB_LOBJS)
endif
ifdef HAVE_DTRACE
ifdef DTRACE_PROBE_OBJ
ifndef DTRACE_LIB_DEPENDENT
$(DTRACE_PROBE_OBJ): $(OBJS)
dtrace -G -C -32 -s $(MOZILLA_DTRACE_SRC) -o $(DTRACE_PROBE_OBJ) $(OBJS)
endif
endif
endif
# On Darwin (Mac OS X), dwarf2 debugging uses debug info left in .o files,
# so instead of deleting .o files after repacking them into a dylib, we make
# symlinks back to the originals. The symlinks are a no-op for stabs debugging,
@ -1078,17 +1087,17 @@ ifdef SHARED_LIBRARY_LIBS
@for lib in $(SHARED_LIBRARY_LIBS); do $(AR_EXTRACT) $${lib}; $(CLEANUP2); done
endif # SHARED_LIBRARY_LIBS
endif # NO_LD_ARCHIVE_FLAGS
ifdef NEED_DTRACE_PROBE_OBJ
ifdef DTRACE_LIB_DEPENDENT
@rm -f $(PROBE_LOBJS)
@for lib in $(MOZILLA_PROBE_LIBS); do $(AR_EXTRACT) $${lib}; $(CLEANUP2); done
dtrace -G -C -32 -s $(MOZILLA_DTRACE_SRC) -o $(NEED_DTRACE_PROBE_OBJ) $(PROBE_LOBJS)
dtrace -G -C -32 -s $(MOZILLA_DTRACE_SRC) -o $(DTRACE_PROBE_OBJ) $(PROBE_LOBJS)
@for lib in $(MOZILLA_PROBE_LIBS); do \
ofiles=`$(AR_LIST) $${lib}`; \
$(AR_DELETE) $${lib} $$ofiles; \
done
$(MKSHLIB) $(SHLIB_LDSTARTFILE) $(OBJS) $(LOBJS) $(SUB_SHLOBJS) $(NEED_DTRACE_PROBE_OBJ) $(PROBE_LOBJS) $(RESFILE) $(LDFLAGS) $(EXTRA_DSO_LDOPTS) $(OS_LIBS) $(EXTRA_LIBS) $(DEF_FILE) $(SHLIB_LDENDFILE)
$(MKSHLIB) $(SHLIB_LDSTARTFILE) $(OBJS) $(LOBJS) $(SUB_SHLOBJS) $(DTRACE_PROBE_OBJ) $(PROBE_LOBJS) $(RESFILE) $(LDFLAGS) $(EXTRA_DSO_LDOPTS) $(OS_LIBS) $(EXTRA_LIBS) $(DEF_FILE) $(SHLIB_LDENDFILE)
@rm -f $(PROBE_LOBJS)
@rm -f $(NEED_DTRACE_PROBE_OBJ)
@rm -f $(DTRACE_PROBE_OBJ)
@for lib in $(MOZILLA_PROBE_LIBS); do \
if [ -L $${lib} ]; then rm -f `readlink $${lib}`; fi; \
done
@ -1096,7 +1105,7 @@ ifdef NEED_DTRACE_PROBE_OBJ
else
$(MKSHLIB) $(SHLIB_LDSTARTFILE) $(OBJS) $(DTRACE_PROBE_OBJ) $(LOBJS) $(SUB_SHLOBJS) $(RESFILE) $(LDFLAGS) $(EXTRA_DSO_LDOPTS) $(OS_LIBS) $(EXTRA_LIBS) $(DEF_FILE) $(SHLIB_LDENDFILE)
endif # NEED_DTRACE_PROBE_OBJ
endif # DTRACE_LIB_DEPENDENT
ifeq (_WINNT,$(GNU_CC)_$(OS_ARCH))
ifdef MSMANIFEST_TOOL

Просмотреть файл

@ -103,6 +103,11 @@ CSRCS = \
prmjtime.c \
$(NULL)
ifdef HAVE_DTRACE
CSRCS += \
jsdtracef.c
endif
EXPORTS = \
jsautocfg.h \
jsautokw.h \
@ -152,6 +157,13 @@ EXPORTS = \
jsxml.h \
$(NULL)
ifdef HAVE_DTRACE
EXPORTS += \
jsdtracef.h \
javascript-trace.h \
$(NULL)
endif
ifeq (,$(filter-out WINNT WINCE,$(OS_ARCH)))
EXPORTS += jscpucfg.h
endif
@ -202,6 +214,11 @@ JSJAVA_CFLAGS = \
HOST_SIMPLE_PROGRAMS += host_jskwgen$(HOST_BIN_SUFFIX)
GARBAGE += jsautokw.h host_jskwgen$(HOST_BIN_SUFFIX)
ifdef HAVE_DTRACE
DTRACE_PROBE_OBJ = $(LIBRARY_NAME)-dtrace.$(OBJ_SUFFIX)
MOZILLA_DTRACE_SRC = $(srcdir)/javascript-trace.d
endif
include $(topsrcdir)/config/rules.mk
DEFINES += -DEXPORT_JS_API
@ -392,3 +409,11 @@ host_jskwgen.$(OBJ_SUFFIX): jsconfig.h jskeyword.tbl
jsautokw.h: host_jskwgen$(HOST_BIN_SUFFIX)
./host_jskwgen$(HOST_BIN_SUFFIX) $@
ifdef HAVE_DTRACE
javascript-trace.h: $(srcdir)/javascript-trace.d
dtrace -h -s $(srcdir)/javascript-trace.d -o javascript-trace.h.in
sed 's/if _DTRACE_VERSION/ifdef INCLUDE_MOZILLA_DTRACE/' \
javascript-trace.h.in > javascript-trace.h
endif

71
js/src/javascript-trace.d Normal file
Просмотреть файл

@ -0,0 +1,71 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* Copyright (C) 2007 Sun Microsystems, Inc. All Rights Reserved.
*
* Alternatively, the contents of this file may be used under the terms of
* either the GNU General Public License Version 2 or later (the "GPL"), or
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
/*
* javascript provider probes
*
* function-entry (filename, classname, funcname)
* function-info (filename, classname, funcname, lineno,
* runfilename, runlineno)
* function-args (filename, classname, funcname, argc, argv, argv0,
* argv1, argv2, argv3, argv4)
* function-rval (filename, classname, funcname, lineno, rval, rval0)
* function-return (filename, classname, funcname)
* object-create-start (filename, classname)
* object-create (filename, classname, *object, rlineno)
* object-create-done (filename, classname)
* object-finalize (NULL, classname, *object)
* execute-start (filename, lineno)
* execute-done (filename, lineno)
*/
provider javascript {
probe function__entry(char *, char *, char *);
probe function__info(char *, char *, char *, int, char *, int);
probe function__args(char *, char *, char *, int, void *, void *, void *,
void *, void *, void *);
probe function__rval(char *, char *, char *, int, void *, void *);
probe function__return(char *, char *, char *);
probe object__create__start(char *, char *);
probe object__create__done(char *, char *);
probe object__create(char *, char *, uintptr_t, int);
probe object__finalize(char *, char *, uintptr_t);
probe execute__start(char *, int);
probe execute__done(char *, int);
};
/*
#pragma D attributes Unstable/Unstable/Common provider mozilla provider
#pragma D attributes Private/Private/Unknown provider mozilla module
#pragma D attributes Private/Private/Unknown provider mozilla function
#pragma D attributes Unstable/Unstable/Common provider mozilla name
#pragma D attributes Unstable/Unstable/Common provider mozilla args
*/

311
js/src/jsdtracef.c Normal file
Просмотреть файл

@ -0,0 +1,311 @@
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
* vim: set ts=8 sw=4 et tw=80:
*
* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* Copyright (C) 2007 Sun Microsystems, Inc. All Rights Reserved.
*
* Contributor(s):
* Brendan Eich <brendan@mozilla.org>
*
* Alternatively, the contents of this file may be used under the terms of
* either of the GNU General Public License Version 2 or later (the "GPL"),
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#include "jsapi.h"
#include "jsutil.h"
#include "jsatom.h"
#include "jscntxt.h"
#include "jsdbgapi.h"
#include "jsfun.h"
#include "jsinterp.h"
#include "jsobj.h"
#include "jsscript.h"
#include "jsstr.h"
#include "jsdtracef.h"
#include <sys/types.h>
#define TYPEOF(cx,v) (JSVAL_IS_NULL(v) ? JSTYPE_NULL : JS_TypeOfValue(cx,v))
static char dempty[] = "<null>";
char *
jsdtrace_filename(JSStackFrame *fp)
{
while (fp && fp->script == NULL)
fp = fp->down;
return (fp && fp->script && fp->script->filename)
? (char *)fp->script->filename
: dempty;
}
int
jsdtrace_linenumber(JSContext *cx, JSStackFrame *fp)
{
while (fp && fp->script == NULL)
fp = fp->down;
return (fp && fp->script && fp->pc)
? js_PCToLineNumber(cx, fp->script, fp->pc)
: -1;
}
/*
* This function is used to convert function arguments and return value (jsval)
* into the following based on each value's type tag:
*
* jsval returned
* -------------------
* STRING -> char *
* INT -> int
* DOUBLE -> double *
* BOOLEAN -> int
* OBJECT -> void *
*
* All are presented as void * for DTrace consumers to use, after shifting or
* masking out the JavaScript type bits. This allows D scripts to use ints and
* booleans directly and copyinstr() for string arguments, when types are known
* beforehand.
*
* This is used by the function-args and function-rval probes, which also
* provide raw (unmasked) jsvals should type info be useful from D scripts.
*/
void *
jsdtrace_jsvaltovoid(JSContext *cx, jsval argval)
{
JSType type = TYPEOF(cx, argval);
switch (type) {
case JSTYPE_NULL:
case JSTYPE_VOID:
return JS_TYPE_STR(type);
case JSTYPE_BOOLEAN:
return (void *)JSVAL_TO_BOOLEAN(argval);
case JSTYPE_STRING:
return (void *)js_GetStringBytes(cx, JSVAL_TO_STRING(argval));
case JSTYPE_NUMBER:
if (JSVAL_IS_INT(argval))
return (void *)JSVAL_TO_INT(argval);
return JSVAL_TO_DOUBLE(argval);
default:
return JSVAL_TO_GCTHING(argval);
}
/* NOTREACHED */
}
char *
jsdtrace_function_name(JSContext *cx, JSStackFrame *fp, JSFunction *fun)
{
JSAtom *atom;
JSScript *script;
jsbytecode *pc;
char *name;
atom = fun->atom;
if (!atom) {
if (fp->fun != fun || !fp->down)
return dempty;
script = fp->down->script;
pc = fp->down->pc;
if (!script || !pc)
return dempty;
/*
* An anonymous function called from an active script or interpreted
* function: try to fetch the variable or property name by which the
* anonymous function was invoked. First handle call ops by recovering
* the generating pc for the callee expression at argv[-2].
*/
switch ((JSOp) *pc) {
case JSOP_CALL:
case JSOP_EVAL:
JS_ASSERT(fp->argv == fp->down->sp - (int)GET_ARGC(pc));
pc = (jsbytecode *) fp->argv[-2 - (int)script->depth];
/*
* Be paranoid about bugs to-do with generating pc storage when
* attempting to descend into the operand stack basement.
*/
if ((uintptr_t)(pc - script->code) >= script->length)
return dempty;
break;
}
switch ((JSOp) *pc) {
case JSOP_CALLNAME:
case JSOP_CALLPROP:
case JSOP_NAME:
case JSOP_SETNAME:
case JSOP_GETPROP:
case JSOP_SETPROP:
GET_ATOM_FROM_BYTECODE(script, pc, 0, atom);
break;
case JSOP_CALLELEM:
case JSOP_GETELEM:
case JSOP_SETELEM:
case JSOP_CALLGVAR:
case JSOP_GETGVAR:
case JSOP_SETGVAR:
case JSOP_CALLVAR:
case JSOP_CALLARG:
case JSOP_CALLLOCAL:
/* FIXME: try to recover a name from these ops. */
/* FALL THROUGH */
default:
return dempty;
}
}
name = (char *)js_GetStringBytes(cx, ATOM_TO_STRING(atom));
return name ? name : dempty;
}
/*
* These functions call the DTrace macros for the JavaScript USDT probes.
* Originally this code was inlined in the JavaScript code; however since
* a number of operations are called, these have been placed into functions
* to reduce any negative compiler optimization effect that the addition of
* a number of usually unused lines of code would cause.
*/
void
jsdtrace_function_entry(JSContext *cx, JSStackFrame *fp, JSFunction *fun)
{
JAVASCRIPT_FUNCTION_ENTRY(
jsdtrace_filename(fp),
fun->clasp ? (char *)fun->clasp->name : dempty,
jsdtrace_function_name(cx, fp, fun)
);
}
void
jsdtrace_function_info(JSContext *cx, JSStackFrame *fp, JSStackFrame *dfp,
JSFunction *fun)
{
JAVASCRIPT_FUNCTION_INFO(
jsdtrace_filename(fp),
fun->clasp ? (char *)fun->clasp->name : dempty,
jsdtrace_function_name(cx, fp, fun),
fp->script->lineno,
jsdtrace_filename(dfp),
jsdtrace_linenumber(cx, dfp)
);
}
void
jsdtrace_function_args(JSContext *cx, JSStackFrame *fp, JSFunction *fun)
{
JAVASCRIPT_FUNCTION_ARGS(
jsdtrace_filename(fp),
fun->clasp ? (char *)fun->clasp->name : dempty,
jsdtrace_function_name(cx, fp, fun),
fp->argc, (void *)fp->argv,
(fp->argc > 0) ? jsdtrace_jsvaltovoid(cx, fp->argv[0]) : 0,
(fp->argc > 1) ? jsdtrace_jsvaltovoid(cx, fp->argv[1]) : 0,
(fp->argc > 2) ? jsdtrace_jsvaltovoid(cx, fp->argv[2]) : 0,
(fp->argc > 3) ? jsdtrace_jsvaltovoid(cx, fp->argv[3]) : 0,
(fp->argc > 4) ? jsdtrace_jsvaltovoid(cx, fp->argv[4]) : 0
);
}
void
jsdtrace_function_rval(JSContext *cx, JSStackFrame *fp, JSFunction *fun)
{
JAVASCRIPT_FUNCTION_RVAL(
jsdtrace_filename(fp),
fun->clasp ? (char *)fun->clasp->name : dempty,
jsdtrace_function_name(cx, fp, fun),
jsdtrace_linenumber(cx, fp), (void *)fp->rval,
jsdtrace_jsvaltovoid(cx, fp->rval)
);
}
void
jsdtrace_function_return(JSContext *cx, JSStackFrame *fp, JSFunction *fun)
{
JAVASCRIPT_FUNCTION_RETURN(
jsdtrace_filename(fp),
fun->clasp ? (char *)fun->clasp->name : dempty,
jsdtrace_function_name(cx, fp, fun)
);
}
void
jsdtrace_object_create_start(JSStackFrame *fp, JSClass *clasp)
{
JAVASCRIPT_OBJECT_CREATE_START(jsdtrace_filename(fp), (char *)clasp->name);
}
void
jsdtrace_object_create_done(JSStackFrame *fp, JSClass *clasp)
{
JAVASCRIPT_OBJECT_CREATE_DONE(jsdtrace_filename(fp), (char *)clasp->name);
}
void
jsdtrace_object_create(JSContext *cx, JSClass *clasp, JSObject *obj)
{
JAVASCRIPT_OBJECT_CREATE(
jsdtrace_filename(cx->fp),
(char *)clasp->name,
(uintptr_t)obj,
jsdtrace_linenumber(cx, cx->fp)
);
}
void
jsdtrace_object_finalize(JSObject *obj)
{
JSClass *clasp;
clasp = LOCKED_OBJ_GET_CLASS(obj);
/* the first arg is NULL - reserved for future use (filename?) */
JAVASCRIPT_OBJECT_FINALIZE(NULL, (char *)clasp->name, (uintptr_t)obj);
}
void
jsdtrace_execute_start(JSScript *script)
{
JAVASCRIPT_EXECUTE_START(
script->filename ? (char *)script->filename : dempty,
script->lineno
);
}
void
jsdtrace_execute_done(JSScript *script)
{
JAVASCRIPT_EXECUTE_DONE(
script->filename ? (char *)script->filename : dempty,
script->lineno
);
}

77
js/src/jsdtracef.h Normal file
Просмотреть файл

@ -0,0 +1,77 @@
/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
* vim: set ts=8 sw=4 et tw=80:
*
* ***** BEGIN LICENSE BLOCK *****
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
*
* The contents of this file are subject to the Mozilla Public License Version
* 1.1 (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
* http://www.mozilla.org/MPL/
*
* Software distributed under the License is distributed on an "AS IS" basis,
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
* for the specific language governing rights and limitations under the
* License.
*
* Copyright (C) 2007 Sun Microsystems, Inc. All Rights Reserved.
*
* Contributor(s):
* Brendan Eich <brendan@mozilla.org>
*
* Alternatively, the contents of this file may be used under the terms of
* either of the GNU General Public License Version 2 or later (the "GPL"),
* or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
* in which case the provisions of the GPL or the LGPL are applicable instead
* of those above. If you wish to allow use of your version of this file only
* under the terms of either the GPL or the LGPL, and not to allow others to
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
#include "javascript-trace.h"
#include "jspubtd.h"
#include "jsprvtd.h"
#ifndef _JSDTRACEF_H
#define _JSDTRACEF_H
extern void
jsdtrace_function_entry(JSContext *cx, JSStackFrame *fp, JSFunction *fun);
extern void
jsdtrace_function_info(JSContext *cx, JSStackFrame *fp, JSStackFrame *dfp,
JSFunction *fun);
extern void
jsdtrace_function_args(JSContext *cx, JSStackFrame *fp, JSFunction *fun);
extern void
jsdtrace_function_rval(JSContext *cx, JSStackFrame *fp, JSFunction *fun);
extern void
jsdtrace_function_return(JSContext *cx, JSStackFrame *fp, JSFunction *fun);
extern void
jsdtrace_object_create_start(JSStackFrame *fp, JSClass *clasp);
extern void
jsdtrace_object_create_done(JSStackFrame *fp, JSClass *clasp);
extern void
jsdtrace_object_create(JSContext *cx, JSClass *clasp, JSObject *obj);
extern void
jsdtrace_object_finalize(JSObject *obj);
extern void
jsdtrace_execute_start(JSScript *script);
extern void
jsdtrace_execute_done(JSScript *script);
#endif /* _JSDTRACE_H */

Просмотреть файл

@ -69,6 +69,10 @@
#include "jsscript.h"
#include "jsstr.h"
#ifdef INCLUDE_MOZILLA_DTRACE
#include "jsdtracef.h"
#endif
#if JS_HAS_XML_SUPPORT
#include "jsxml.h"
#endif
@ -1533,6 +1537,11 @@ js_Execute(JSContext *cx, JSObject *chain, JSScript *script,
JSObject *obj, *tmp;
JSBool ok;
#ifdef INCLUDE_MOZILLA_DTRACE
if (JAVASCRIPT_EXECUTE_START_ENABLED())
jsdtrace_execute_start(script);
#endif
hook = cx->debugHooks->executeHook;
hookData = mark = NULL;
oldfp = cx->fp;
@ -1569,8 +1578,10 @@ js_Execute(JSContext *cx, JSObject *chain, JSScript *script,
frame.nvars += JS_SCRIPT_REGEXPS(script)->length;
if (frame.nvars != 0) {
frame.vars = js_AllocRawStack(cx, frame.nvars, &mark);
if (!frame.vars)
return JS_FALSE;
if (!frame.vars) {
ok = JS_FALSE;
goto out;
}
memset(frame.vars, 0, frame.nvars * sizeof(jsval));
} else {
frame.vars = NULL;
@ -1637,6 +1648,11 @@ js_Execute(JSContext *cx, JSObject *chain, JSScript *script,
oldfp->dormantNext = NULL;
}
out:
#ifdef INCLUDE_MOZILLA_DTRACE
if (JAVASCRIPT_EXECUTE_DONE_ENABLED())
jsdtrace_execute_done(script);
#endif
return ok;
}
@ -2614,6 +2630,14 @@ interrupt:
ok &= js_PutArgsObject(cx, fp);
}
#ifdef INCLUDE_MOZILLA_DTRACE
/* DTrace function return, inlines */
if (JAVASCRIPT_FUNCTION_RVAL_ENABLED())
jsdtrace_function_rval(cx, fp, fp->fun);
if (JAVASCRIPT_FUNCTION_RETURN_ENABLED())
jsdtrace_function_return(cx, fp, fp->fun);
#endif
/* Restore context version only if callee hasn't set version. */
if (JS_LIKELY(cx->version == currentVersion)) {
currentVersion = ifp->callerVersion;
@ -4038,6 +4062,16 @@ interrupt:
inlineCallCount++;
JS_RUNTIME_METER(rt, inlineCalls);
#ifdef INCLUDE_MOZILLA_DTRACE
/* DTrace function entry, inlines */
if (JAVASCRIPT_FUNCTION_ENTRY_ENABLED())
jsdtrace_function_entry(cx, fp, fun);
if (JAVASCRIPT_FUNCTION_INFO_ENABLED())
jsdtrace_function_info(cx, fp, fp->down, fun);
if (JAVASCRIPT_FUNCTION_ARGS_ENABLED())
jsdtrace_function_args(cx, fp, fun);
#endif
/* Load first op and dispatch it (safe since JSOP_STOP). */
op = (JSOp) *pc;
DO_OP();
@ -4053,6 +4087,18 @@ interrupt:
goto out;
}
#ifdef INCLUDE_MOZILLA_DTRACE
/* DTrace function entry, non-inlines */
if (VALUE_IS_FUNCTION(cx, lval)) {
if (JAVASCRIPT_FUNCTION_ENTRY_ENABLED())
jsdtrace_function_entry(cx, fp, fun);
if (JAVASCRIPT_FUNCTION_INFO_ENABLED())
jsdtrace_function_info(cx, fp, fp, fun);
if (JAVASCRIPT_FUNCTION_ARGS_ENABLED())
jsdtrace_function_args(cx, fp, fun);
}
#endif
if (fun->flags & JSFUN_FAST_NATIVE) {
JS_ASSERT(fun->u.n.extra == 0);
if (argc < fun->u.n.minargs) {
@ -4080,6 +4126,14 @@ interrupt:
PRIMITIVE_THIS_TEST(fun, vp[1]));
ok = ((JSFastNative) fun->u.n.native)(cx, argc, vp);
#ifdef INCLUDE_MOZILLA_DTRACE
if (VALUE_IS_FUNCTION(cx, lval)) {
if (JAVASCRIPT_FUNCTION_RVAL_ENABLED())
jsdtrace_function_rval(cx, fp, fun);
if (JAVASCRIPT_FUNCTION_RETURN_ENABLED())
jsdtrace_function_return(cx, fp, fun);
}
#endif
if (!ok)
goto out;
sp = vp + 1;
@ -4090,6 +4144,15 @@ interrupt:
do_invoke:
ok = js_Invoke(cx, argc, vp, 0);
#ifdef INCLUDE_MOZILLA_DTRACE
/* DTrace function return, non-inlines */
if (VALUE_IS_FUNCTION(cx, lval)) {
if (JAVASCRIPT_FUNCTION_RVAL_ENABLED())
jsdtrace_function_rval(cx, fp, fun);
if (JAVASCRIPT_FUNCTION_RETURN_ENABLED())
jsdtrace_function_return(cx, fp, fun);
}
#endif
sp = vp + 1;
vp[-depth] = (jsval)pc;
LOAD_INTERRUPT_HANDLER(cx);

Просмотреть файл

@ -83,6 +83,10 @@
#include "jsxdrapi.h"
#endif
#ifdef INCLUDE_MOZILLA_DTRACE
#include "jsdtracef.h"
#endif
#ifdef JS_THREADSAFE
#define NATIVE_DROP_PROPERTY js_DropProperty
@ -2511,16 +2515,21 @@ js_NewObject(JSContext *cx, JSClass *clasp, JSObject *proto, JSObject *parent)
uint32 nslots, i;
JSTempValueRooter tvr;
#ifdef INCLUDE_MOZILLA_DTRACE
if (JAVASCRIPT_OBJECT_CREATE_START_ENABLED())
jsdtrace_object_create_start(cx->fp, clasp);
#endif
/* Bootstrap the ur-object, and make it the default prototype object. */
if (!proto) {
if (!js_GetClassId(cx, clasp, &id))
return NULL;
goto earlybad;
if (!js_GetClassPrototype(cx, parent, id, &proto))
return NULL;
goto earlybad;
if (!proto &&
!js_GetClassPrototype(cx, parent, INT_TO_JSID(JSProto_Object),
&proto)) {
return NULL;
goto earlybad;
}
}
@ -2536,7 +2545,7 @@ js_NewObject(JSContext *cx, JSClass *clasp, JSObject *proto, JSObject *parent)
*/
obj = (JSObject *) js_NewGCThing(cx, GCX_OBJECT, sizeof(JSObject));
if (!obj)
return NULL;
goto earlybad;
/*
* Initialize all JSObject fields before doing any operation that can
@ -2621,11 +2630,26 @@ js_NewObject(JSContext *cx, JSClass *clasp, JSObject *proto, JSObject *parent)
out:
JS_POP_TEMP_ROOT(cx, &tvr);
cx->weakRoots.newborn[GCX_OBJECT] = obj;
#ifdef INCLUDE_MOZILLA_DTRACE
if (JAVASCRIPT_OBJECT_CREATE_ENABLED())
jsdtrace_object_create(cx, clasp, obj);
if (JAVASCRIPT_OBJECT_CREATE_DONE_ENABLED())
jsdtrace_object_create_done(cx->fp, clasp);
#endif
return obj;
bad:
obj = NULL;
goto out;
earlybad:
#ifdef INCLUDE_MOZILLA_DTRACE
if (JAVASCRIPT_OBJECT_CREATE_ENABLED())
jsdtrace_object_create(cx, clasp, NULL);
if (JAVASCRIPT_OBJECT_CREATE_DONE_ENABLED())
jsdtrace_object_create_done(cx->fp, clasp);
#endif
return NULL;
}
JS_BEGIN_EXTERN_C
@ -2874,6 +2898,11 @@ js_FinalizeObject(JSContext *cx, JSObject *obj)
/* Finalize obj first, in case it needs map and slots. */
GC_AWARE_GET_CLASS(cx, obj)->finalize(cx, obj);
#ifdef INCLUDE_MOZILLA_DTRACE
if (JAVASCRIPT_OBJECT_FINALIZE_ENABLED())
jsdtrace_object_finalize(obj);
#endif
/* Drop map and free slots. */
js_DropObjectMap(cx, map, obj);
FreeSlots(cx, obj);