btraceio / btrace

BTrace - a safe, dynamic tracing tool for the Java platform
5.81k stars 960 forks source link

Learning the BTrace Basics #224

Closed moonlitSpider closed 6 years ago

moonlitSpider commented 8 years ago

Well, I've decided that since I can't get anything to work with BTrace, that I should back up and try some simple examples against a simple Java program running locally on my Windows 7. (That is, I am forgetting about trying to get btrace working against containerized Virgo Tomcat on a Linux node - that's out of my depth).

So....I wrote a simple java program and saved it as a jar file. Its "main" method calls another method (also static) called makeFiles. makeFiles sleeps for 5 seconds and that does a File.createNewFile. It does this "forever".

I found this example on the Web:

import com.sun.btrace.annotations.*;
import com.sun.btrace.BTraceUtils;

@BTrace

public class HelloWorld {
@OnMethod(clazz="java.io.File",method="")
public static void onNewFileCreated(String fileName) {
   BTraceUtils.println("New file is being created");
   BTraceUtils.println(fileName);
 }
}

I pasted it into JVisualVM where it compiles cleanly. But, after starting the jar file and seeing it appear in JVisualVM's left pane, there is no context menu entry for "Trace Application". Please note that there IS such an entry for another JVM (the one associated with the Eclipse editor). I suppose this has to do with Java versions. I started the 1.7.0_03 version of JVisualVM. The class/jar in question was compiled with 1.7.

Any idea what I am doing wrong?

Thanks.
moonlitSpider commented 8 years ago

So I upgraded to Java 1.8.0_92 and tried again.

After installing the BTrace plugin into JVisualVM, I compiled therein the script above (see below), but no output, e.g., the two println statements, is produced.

Please note that the monitored program is definitely creating files.

I'd be grateful for any light on this.

Thanks.

### ** Compiling the BTrace script ...
*** Compiled
** Instrumenting 1 classes ...
*** Done
** BTrace up&running

*** Done
** BTrace up&running
jbachorik commented 8 years ago

You need to run the app on a full JDK.

moonlitSpider commented 8 years ago

Not sure I follow.

I create a jar file & run it outside of the eclipse environment.

That is, I am running "java -jar" where the java command is in the bin directory of the JDK distro.

So I am running the app on full JDK, no?

Thank you.

On May 6, 2016, at 2:27 PM, "Jaroslav Bachorik" notifications@github.com<mailto:notifications@github.com> wrote:

You need to run the app on a full JDK.

You are receiving this because you authored the thread. Reply to this email directly or view it on GitHubhttps://github.com/btraceio/btrace/issues/224#issuecomment-217522017

CATALOGIC SOFTWARE, ATTENTION::----- The information contained in this message (including any files transmitted with this message) may contain proprietary, trade secret or other confidential and/or legally privileged information. Any pricing information contained in this message or in any files transmitted with this message is always confidential and cannot be shared with any third parties without prior written approval from Catalogic Software. This message is intended to be read only by the individual or entity to whom it is addressed or by their designee. If the reader of this message is not the intended recipient, you are on notice that any use, disclosure, copying or distribution of this message, in any form, is strictly prohibited. If you have received this message in error, please immediately notify the sender and/or Catalogic Software and destroy all copies of this message in your possession, custody or control.

jbachorik commented 8 years ago

On May 6, 2016 8:46 PM, "moonlitSpider" notifications@github.com wrote:

Not sure I follow.

I create a jar file & run it outside of the eclipse environment.

That is, I am running "java -jar" where the java command is in the bin directory of the JDK distro.

So I am running the app on full JDK, no?

Not necessarily. Eg. on ubuntu only JRE is installed by default and you must specifically install JDK.

About your second problem - File.createFile() method takes no argument. Your onmethod probe, on the other hand, is trying to match File.createFile(string) and that does not exist. You will need to use @Self annotated parameter to get hold of the File instance and extract the filename from there. Please, refer to the samples to see the @Self usage.

Cheers,

-JB-

Thank you.

On May 6, 2016, at 2:27 PM, "Jaroslav Bachorik" <notifications@github.com mailto:notifications@github.com> wrote:

You need to run the app on a full JDK.

You are receiving this because you authored the thread. Reply to this email directly or view it on GitHub< https://github.com/btraceio/btrace/issues/224#issuecomment-217522017>

CATALOGIC SOFTWARE, ATTENTION::----- The information contained in this message (including any files transmitted with this message) may contain proprietary, trade secret or other confidential and/or legally privileged information. Any pricing information contained in this message or in any files transmitted with this message is always confidential and cannot be shared with any third parties without prior written approval from Catalogic Software. This message is intended to be read only by the individual or entity to whom it is addressed or by their designee. If the reader of this message is not the intended recipient, you are on notice that any use, disclosure, copying or distribution of this message, in any form, is strictly prohibited. If you have received this message in error, please immediately notify the sender and/or Catalogic Software and destroy all copies of this message in your possession, custody or control.

— You are receiving this because you commented.

Reply to this email directly or view it on GitHub

moonlitSpider commented 8 years ago

Hi Jaroslav,

Trying to simplify things, I am presently using Windows 7 to try what I hoped would be some very simple btrace cases. So Ubuntu is not in the mix. If I can get things working on Windows, and thereby learn some btrace, I will return to my original, complex problem (containerized Virgo on Ubuntu).

I will try what you say re @Self to match the File.createNewFile() call.

Thanks for your help.

-Paul

moonlitSpider commented 8 years ago

Hmm....got it working:

public class HelloWorld { @OnMethod(clazz="java.io.File",method="createNewFile") public static void onNewFileCreated(@Self java.io.File file) { BTraceUtils.println("New file is being created"); BTraceUtils.println(file); } }

But it's not clear to me why the 2nd println prints the name of the file I am creating. I mean, that's what I wanted to see, but I don't understand what's going on under the covers. Put otherwise, how is the variable 'file' being interpreted by btrace?

Thanks again.

jbachorik commented 8 years ago

On May 6, 2016 10:36 PM, "moonlitSpider" notifications@github.com wrote:

Hmm....got it working:

public class HelloWorld { @OnMethod(clazz="java.io.File",method="createNewFile") public static void onNewFileCreated(@Self java.io.File file) {

BTraceUtils.println("New file is being created"); BTraceUtils.println(file); } }

But it's not clear to me why the 2nd println prints the name of the file I am creating. I mean, that's what I wanted to see, but I don't understand what's going on under the covers. Put otherwise, how is the variable 'file' being interpreted by btrace?

This one is trivial. The value is implicitly converted to string, calling the instance toString() method. Coincidentally, the string representation of a File instance is its name. Please, be aware that this implicit toString() call in BTrace is applied only to classes from rt.jar (a bit of simplification, but generally true).

-JB-

Thanks again.

— You are receiving this because you commented.

Reply to this email directly or view it on GitHub

moonlitSpider commented 8 years ago

Understood (and pretty much what I supposed); thanks again.

jbachorik commented 8 years ago

A good place to start is the wiki. I know it's not a step-by-step tutorial but should explain everything necessary to start.

moonlitSpider commented 8 years ago

Thank you.

Funny you bring this up because I've been looking around for a good starting point with Btrace.

I am curious about the provenance of this tool. It seems to go back a few years and over that time has had various champions, you, I suppose, being its current champion.

If I'm right about its history, then this may account for the seeming lack of comprehensive documentation, e.g., current user guides and programming guides. There really seems to be a lot to learn.

What about the btrace project at the Kenai web pages? Is that stuff still current or has it been superceded?

Cordially,

Paul

jbachorik commented 8 years ago

Well, I was the 'champion' since Sundar (the original author) moved to other, more interesting to him, projects. If I remember well I was the maintainer of BTrace since 2009.

The main reason for the lacking documentation is the fact that I was working on it only during my free time and when I had a chance I better invested that time into fixes, improvements and new features. Basically it is the curse of hobby open source projects - nobody really feels like contributing to docs.

Actually, I did prepare a step-by-step tutorial to start with BTrace but it was paid for by a 3rd party company so I need to clear with them first before I put it anywhere in open.

Regarding Kenai - it's been mostly zombified since I moved the project to GitHub. Kenai forge was left dead by Oracle, moving back to java.net was problematic, mostly because there once were such a project (before moving to 'progressive' kenai.com) and the java.net support stuff was also cut down.

After doing a small survey I moved the project to GitHub. Probably a wise decision considering that java.net is being discontinued as we are speaking.

moonlitSpider commented 8 years ago

Hi Jaroslav,

Thanks much for this history. I readily understand the "curse" you describe. Nonetheless, thank you for your efforts on this tool.

My interest in btrace, which goes back several years, is rooted in an article I read many years ago in the IBM Systems Journal. This article described a state-sampling monitor which allowed one to determine where most time was being spent in a program. Conceptually, it's simple:

  1. the monitor runs a timer and wakes up periodically.
  2. upon waking it examines threads of interest to see if they are running (in flight on a processor) or waiting to run (in processor run queue), or waiting.
  3. if they're waiting, then it figures out what resource they're waiting for
  4. keeps a table of these samples by thread

When you stop the monitor it dumps the table and with some simple statistical methods you can figure out who's spending time and where.

Being an old mainframe assembly language programmer, and quite familiar with OS internals, it was easy for me to write such a program. But I've always wanted to provide such instrumentation against a Java program & that's where btrace comes in.

If you have the time and inclination I'd very much appreciate some guidance on how to do this with btrace.

[Aside: Several years ago, when I remembered more about Java internals, I think I recall being stumped by analyzing Java thread wait states, i.e., I recall something about Java monitors as a means of synchronizing on external events, e.g., I/O. But I could never find a way of determining what device a thread was waiting on.]

And then there's the matter of the target program running OSGI Virgo in a Docker container. Still don't know how to resolve that one.

Thanks again.

-Paul


From: Jaroslav Bachorik notifications@github.com Sent: Monday, May 9, 2016 2:17:36 AM To: btraceio/btrace Cc: Bell, Paul; Author Subject: Re: [btraceio/btrace] Learning the BTrace Basics (#224)

Well, I was the 'champion' since Sundar (the original author) moved to other, more interesting to him, projects. If I remember well I was the maintainer of BTrace since 2009.

The main reason for the lacking documentation is the fact that I was working on it only during my free time and when I had a chance I better invested that time into fixes, improvements and new features. Basically it is the curse of hobby open source projects - nobody really feels like contributing to docs.

Actually, I did prepare a step-by-step tutorial to start with BTrace but it was paid for by a 3rd party company so I need to clear with them first before I put it anywhere in open.

Regarding Kenai - it's been mostly zombified since I moved the project to GitHub. Kenai forge was left dead by Oracle, moving back to java.net was problematic, mostly because there once were such a project (before moving to 'progressive' kenai.com) and the java.net support stuff was also cut down.

After doing a small survey I moved the project to GitHub. Probably a wise decision considering that java.net is being discontinued as we are speaking.

You are receiving this because you authored the thread. Reply to this email directly or view it on GitHubhttps://github.com/btraceio/btrace/issues/224#issuecomment-217784034

CATALOGIC SOFTWARE, ATTENTION::----- The information contained in this message (including any files transmitted with this message) may contain proprietary, trade secret or other confidential and/or legally privileged information. Any pricing information contained in this message or in any files transmitted with this message is always confidential and cannot be shared with any third parties without prior written approval from Catalogic Software. This message is intended to be read only by the individual or entity to whom it is addressed or by their designee. If the reader of this message is not the intended recipient, you are on notice that any use, disclosure, copying or distribution of this message, in any form, is strictly prohibited. If you have received this message in error, please immediately notify the sender and/or Catalogic Software and destroy all copies of this message in your possession, custody or control.

jbachorik commented 8 years ago

IMO, this part 'then it figures out what resource they're waiting for' is almost impossible to get done in pure java reliably. You could use BTrace and instrument all the methods that could potentially leading to a blocking call, storing the resource identifier in a @TLS variable (it will be per-thread) and then check the state of all threads in @OnTimer handler - if a thread is waiting consult the resource identifier stored in the @TLS variable.

The problem is to identify 'all the methods that could potentially leading to a blocking call'.