Default style (Cherry Eve). Switch styles (Capricorn). XML Feed Calendar
All | General
20041209 Thursday December 09, 2004

DTrace & Mozilla

I gave a brief talk about how to use dtrace to debug mozilla on Wed. Here are the examples I used for the talk.

Examples

Ex1. How many files opend by mozilla and what they are?

dtrace -n syscall::open:entry'/execname=="mozilla-bin"/{trace(copyinstr(arg0))}'

Another form:

#!/usr/sbin/dtrace -s

syscall::open:entry
/execname=="mozilla-bin"/
{
  trace(copyinstr(arg0));
}
(# ./open.d)

Highlights:

  • syscall provider - lets you trace every system call entry and return
  • predicate - / ... /
  • copyinstr - copy user process data into the address space of kernel

Ex2. The .mozill bug - which convertor is mozilla using?

#!/usr/sbin/dtrace -s

BEGIN
{
  self->start = 0;
}

/* nsLocalFile::GetPath */
pid$1::__1cLnsLocalFileHGetPath6MrnJnsAString__I_:entry
{
  self->start = 1;
}

pid$1::__1cLnsLocalFileHGetPath6MrnJnsAString__I_:return
{
  self->start = 0;
}

/* http://aggregate.eng/ws/on10_nightly/source/usr/src/lib/libc/port/gen/iconv.c */
pid$1::_icv_iconv:entry
/self->start/
{
  trace(probemod);
}
(# ./iconv.d `pgrep mozilla-bin` (1.4))
(# ./iconv.d `pgrep mozilla-bin` (1.7))

Highlights:

  • pid provider - allows you to trace any instruction in a process
  • D language variable type
    • associative array
    • thread-local variable - self
    • clause-local variable - this
    • built-in variables - execname, probemod, probefunc, pid, etc.

Ex3. Constructor & Destructor

#!/usr/sbin/dtrace -s

BEGIN
{
  self->div = 0;
}

pid$1:libgklayout:__1cQnsHTMLDivElement2t*6M_v_:entry
{
  self->div++;
  printf("Div++: %d", self->div);
}

pid$1:libgklayout:__1cQnsHTMLDivElement2T*6M_v_:entry
{
  self->div--;
  printf("Div--: %d", self->div);
}
(# ./ctordtor.d `pgrep mozilla-bin`)

Highlights:

  • some utilities: nm - symbol lookup; c++filt - C++ symbol demangler
  • no optimized build

Ex4. What's leaked?

#!/usr/sbin/dtrace -s

BEGIN
{
 self->div = 0;
}

pid$1:libgklayout:__1cQnsHTMLDivElement2t*6M_v_:entry
{
 @t[arg0] = count();
 self->div++;
 printf("Div++: %d", self->div);
}

pid$1:libgklayout:__1cQnsHTMLDivElement2T*6M_v_:entry
{
 @t[arg0] = count();
 self->div--;
 printf("Div--: %d", self->div);
}
(# ./count.d `pgrep mozilla-bin`)

Highlights:

  • arg0 - arg9: for entry probe - first ten arguments, int64 (in C++ program, the last argument is always "this".); for return prob - arg1 - return value;
  • aggregating functions
    • count - the number of times called.
    • sum - the total value of specified expressions.
    • quantize - see Ex 6.

Ex5. More aggregations 1 - How many system calls did mozilla make?

dtrace -n syscall:::entry'/execname=="mozilla-bin"/{@t[probefunc] = count()}'

Ex6. More aggregations 2 - How many bytes write to disk for every "write" system call?

dtrace -n syscall::write:entry'/execname=="mozilla-bin"/{@t[execname] = quantize(arg2);}'

Ex7. Timing & aggregations - How many time do js* functions consume?

#!/usr/sbin/dtrace -s

pid$1:libmozjs:js*:entry
{
  time[probefunc] = vtimestamp;
}

pid$1:libmozjs:js*:return
/time[probefunc]/
{
  @t[probefunc] =  sum(vtimestamp - time[probefunc]);
  time[probefunc] = 0;
}
(# ./time.d `pgrep mozilla-bin`)

Ex8. Which gtk functions have been called by gtk_window_new?

#!/usr/sbin/dtrace -Fs

pid$1::$2:entry
{
  self->trace = 1;
}

pid$1::$2:return
/self->trace/
{
  self->trace = 0;
}

pid$1:libgtk-x11-2.0::entry,
pid$1:libgtk-x11-2.0::return
/self->trace/
{
}
(# ./userfunc.d `pgrep mozilla-bin` gtk_window_new)

Ex9. Tracing arbitrary instruction

dtrace -n pid29967:libmozjs:JS_MaybeGC:

Highlights:

  • pid provider can trace any instruction in any user function;
  • useful to determine the code path;

Ex10. Watch the stack - Which files failed to open?

#!/usr/sbin/dtrace -s

syscall::open:entry
/pid == $1/
{
  self->path = copyinstr(arg0);
}

syscall::open:return
/self->path != NULL && arg1 == -1/
{
  printf("open for %s failed!", self->path);
  ustack(30);
}
(# ./badopen.d `pgrep mozilla-bin`)

Highlights:

  • ustack() - records a user stack trace (stack() is for kernel stack);

Ex11. $target - Tracing from the beginning

#!/usr/sbin/dtrace -s

pid$target:libc::entry
{
  @[probefunc] = count();
}
(# dtrace -s libc.d -c date)

Highlights:

  • pid provider can only be used on processes that are already running;

Resources

  • Home page: http://dtrace.eng
  • Mail alias: dtrace-interest
  • Solaris Dynamic Tracing Guide: http://docs.sun.com/app/docs/doc/817-6223?q=dtrace
  • Examples: /usr/demo/dtrace
December 09, 2004 07:26 PM PST Permalink

Comments:

Great to see that we are starting to apply DTrace to specific application. This will increase DTrace mass appeal to first time Solaris Administrator (those who only knew Windows before Solaris 10).

Posted by iwan rahabok on December 09, 2004 at 10:05 PM PST #

[Trackback] Sun Engineer Kyle Yuan shows his mozilla-fu by blogging a bit about how one would use dtrace to grovel through the beast that is Mozilla. Looking forward to seeing some bugzilla reports of performance improvements and memory leaks being plugged due t...

Posted by Yusuf Goolamabbas blog on December 09, 2004 at 11:50 PM PST #

Post a Comment:

Comments are closed for this entry.

Calendar

« November 2009
SunMonTueWedThuFriSat
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
     
       
Today

Links


Navigation


Referers

Today's Page Hits: 8